Sun Aug 6 15:02:25 2006

Asterisk developer's documentation


Main Page | Modules | Alphabetical List | Data Structures | Directories | File List | Data Fields | Globals | Related Pages

app_rpt.c

Go to the documentation of this file.
00001 /*
00002  * Asterisk -- An open source telephony toolkit.
00003  *
00004  * Copyright (C) 2002-2005, Jim Dixon, WB6NIL
00005  *
00006  * Jim Dixon, WB6NIL <jim@lambdatel.com>
00007  * Serious contributions by Steve RoDgers, WA6ZFT <hwstar@rodgers.sdcoxmail.com>
00008  *
00009  * See http://www.asterisk.org for more information about
00010  * the Asterisk project. Please do not directly contact
00011  * any of the maintainers of this project for assistance;
00012  * the project provides a web site, mailing lists and IRC
00013  * channels for your use.
00014  *
00015  * This program is free software, distributed under the terms of
00016  * the GNU General Public License Version 2. See the LICENSE file
00017  * at the top of the source tree.
00018  */
00019 
00020 /*
00021  *
00022  * Radio Repeater / Remote Base program 
00023  *  version 0.37 11/3/05
00024  * 
00025  * See http://www.zapatatelephony.org/app_rpt.html
00026  *
00027  *
00028  * Repeater / Remote Functions:
00029  * "Simple" Mode:  * - autopatch access, # - autopatch hangup
00030  * Normal mode:
00031  * See the function list in rpt.conf
00032  *
00033  *  To send an asterisk (*) while dialing or talking on phone,
00034  *  use the autopatch acess code.
00035  *
00036  *
00037  * status cmds:
00038  *
00039  *  1 - Force ID
00040  *  2 - Give Time of Day
00041  *  3 - Give software Version
00042  *
00043  * cop (control operator) cmds:
00044  *
00045  *  1 - System warm boot
00046  *  2 - System enable
00047  *  3 - System disable
00048  *  4 - Test Tone On
00049  *  5 - Dump System Variables on Console (debug)
00050  *  6 - PTT (phone mode only)
00051  *
00052  * ilink cmds:
00053  *
00054  *  1 - Disconnect specified link
00055  *  2 - Connect specified link -- monitor only
00056  *  3 - Connect specified link -- tranceive
00057  *  4 - Enter command mode on specified link
00058  *  5 - System status
00059  *  6 - Disconnect all links
00060  *
00061  * remote cmds:
00062  *
00063  *  1 - Recall Memory MM  (*000-*099) (Gets memory from rpt.conf)
00064  *  2 - Set VFO MMMMM*KKK*O   (Mhz digits, Khz digits, Offset)
00065  *  3 - Set Rx PL Tone HHH*D*
00066  *  4 - Set Tx PL Tone HHH*D* (Not currently implemented with DHE RBI-1)
00067  *  5 - Link Status (long)
00068  *  6 - Set operating mode M (FM, USB, LSB, AM, etc)
00069  *  100 - RX PL off (Default)
00070  *  101 - RX PL On
00071  *  102 - TX PL Off (Default)
00072  *  103 - TX PL On
00073  *  104 - Low Power
00074  *  105 - Med Power
00075  *  106 - Hi Power
00076  *  107 - Bump Down 20 Hz
00077  *  108 - Bump Down 100 Hz
00078  *  109 - Bump Down 500 Hz
00079  *  110 - Bump Up 20 Hz
00080  *  111 - Bump Up 100 Hz
00081  *  112 - Bump Up 500 Hz
00082  *  113 - Scan Down Slow
00083  *  114 - Scan Down Medium
00084  *  115 - Scan Down Fast
00085  *  116 - Scan Up Slow
00086  *  117 - Scan Up Medium
00087  *  118 - Scan Up Fast
00088  *  119 - Transmit allowing auto-tune
00089  *  140 - Link Status (brief)
00090  *
00091  *
00092 */
00093 
00094 /* The following is JUST GROSS!! There is some soft of underlying problem,
00095    probably in channel_iax2.c, that causes an IAX2 connection to sometimes
00096    stop transmitting randomly. We have been working for weeks to try to
00097    locate it and fix it, but to no avail We finally decided to put our
00098    tail between our legs, and just make the radio system re-connect upon
00099    network failure. This just shouldnt have to be done. For normal operation,
00100    comment-out the following line */
00101 #define  RECONNECT_KLUDGE 
00102 
00103 /* maximum digits in DTMF buffer, and seconds after * for DTMF command timeout */
00104 
00105 #define  MAXDTMF 32
00106 #define  DTMF_TIMEOUT 3
00107 
00108 #define  DISC_TIME 10000  /* report disc after 10 seconds of no connect */
00109 #define  MAX_RETRIES 5
00110 
00111 #define  REDUNDANT_TX_TIME 2000
00112 
00113 #define  RETRY_TIMER_MS 5000
00114 
00115 #define  MAXREMSTR 15
00116 
00117 #define  NODES "nodes"
00118 #define MEMORY "memory"
00119 #define  FUNCTIONS "functions"
00120 #define TELEMETRY "telemetry"
00121 #define MORSE "morse"
00122 #define  FUNCCHAR '*'
00123 #define  ENDCHAR '#'
00124 
00125 #define  DEFAULT_IOBASE 0x378
00126 
00127 #define  MAXCONNECTTIME 5000
00128 
00129 #define MAXNODESTR 300
00130 
00131 #define ACTIONSIZE 32
00132 
00133 #define TELEPARAMSIZE 256
00134 
00135 #define REM_SCANTIME 100
00136 
00137 
00138 enum {REM_OFF,REM_MONITOR,REM_TX};
00139 
00140 enum{ID,PROC,TERM,COMPLETE,UNKEY,REMDISC,REMALREADY,REMNOTFOUND,REMGO,
00141    CONNECTED,CONNFAIL,STATUS,TIMEOUT,ID1, STATS_TIME,
00142    STATS_VERSION, IDTALKOVER, ARB_ALPHA, TEST_TONE, REV_PATCH};
00143 
00144 enum {REM_SIMPLEX,REM_MINUS,REM_PLUS};
00145 
00146 enum {REM_LOWPWR,REM_MEDPWR,REM_HIPWR};
00147 
00148 enum {DC_INDETERMINATE, DC_REQ_FLUSH, DC_ERROR, DC_COMPLETE, DC_DOKEY};
00149 
00150 enum {SOURCE_RPT, SOURCE_LNK, SOURCE_RMT, SOURCE_PHONE, SOURCE_DPHONE};
00151 
00152 enum {DLY_TELEM, DLY_ID, DLY_UNKEY, DLY_CALLTERM};
00153 
00154 enum {REM_MODE_FM,REM_MODE_USB,REM_MODE_LSB,REM_MODE_AM};
00155 
00156 enum {HF_SCAN_OFF,HF_SCAN_DOWN_SLOW,HF_SCAN_DOWN_QUICK,HF_SCAN_DOWN_FAST,HF_SCAN_UP_SLOW,HF_SCAN_UP_QUICK,HF_SCAN_UP_FAST};
00157 
00158 #include "asterisk.h"
00159 
00160 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 7221 $")
00161 
00162 #include <signal.h>
00163 #include <stdio.h>
00164 #include <unistd.h>
00165 #include <string.h>
00166 #include <stdlib.h>
00167 #include <search.h>
00168 #include <sys/types.h>
00169 #include <sys/stat.h>
00170 #include <errno.h>
00171 #include <dirent.h>
00172 #include <ctype.h>
00173 #include <sys/stat.h>
00174 #include <sys/time.h>
00175 #include <sys/file.h>
00176 #include <sys/ioctl.h>
00177 #include <sys/io.h>
00178 #include <math.h>
00179 #include <tonezone.h>
00180 #include <linux/zaptel.h>
00181 #include <netinet/in.h>
00182 #include <arpa/inet.h>
00183 
00184 #include "asterisk/utils.h"
00185 #include "asterisk/lock.h"
00186 #include "asterisk/file.h"
00187 #include "asterisk/logger.h"
00188 #include "asterisk/channel.h"
00189 #include "asterisk/callerid.h"
00190 #include "asterisk/pbx.h"
00191 #include "asterisk/module.h"
00192 #include "asterisk/translate.h"
00193 #include "asterisk/features.h"
00194 #include "asterisk/options.h"
00195 #include "asterisk/cli.h"
00196 #include "asterisk/config.h"
00197 #include "asterisk/say.h"
00198 #include "asterisk/localtime.h"
00199 
00200 static  char *tdesc = "Radio Repeater / Remote Base  version 0.37  11/03/2005";
00201 
00202 static char *app = "Rpt";
00203 
00204 static char *synopsis = "Radio Repeater/Remote Base Control System";
00205 
00206 static char *descrip = 
00207 "  Rpt(nodename[|options]):  Radio Remote Link or Remote Base Link Endpoint Process.\n"
00208 "\n"
00209 "    Not specifying an option puts it in normal endpoint mode (where source\n"
00210 "    IP and nodename are verified).\n"
00211 "\n"
00212 "    Options are as follows:\n"
00213 "\n"
00214 "        X - Normal endpoint mode WITHOUT security check. Only specify\n"
00215 "            this if you have checked security already (like with an IAX2\n"
00216 "            user/password or something).\n"
00217 "\n"
00218 "        Rannounce-string[|timeout[|timeout-destination]] - Amateur Radio\n"
00219 "            Reverse Autopatch. Caller is put on hold, and announcement (as\n"
00220 "            specified by the 'announce-string') is played on radio system.\n"
00221 "            Users of radio system can access autopatch, dial specified\n"
00222 "            code, and pick up call. Announce-string is list of names of\n"
00223 "            recordings, or \"PARKED\" to substitute code for un-parking,\n"
00224 "            or \"NODE\" to substitute node number.\n"
00225 "\n"
00226 "        P - Phone Control mode. This allows a regular phone user to have\n"
00227 "            full control and audio access to the radio system. For the\n"
00228 "            user to have DTMF control, the 'phone_functions' parameter\n"
00229 "            must be specified for the node in 'rpt.conf'. An additional\n"
00230 "            function (cop,6) must be listed so that PTT control is available.\n"
00231 "\n"
00232 "        D - Dumb Phone Control mode. This allows a regular phone user to\n"
00233 "            have full control and audio access to the radio system. In this\n"
00234 "            mode, the PTT is activated for the entire length of the call.\n"
00235 "            For the user to have DTMF control (not generally recomended in\n"
00236 "            this mode), the 'dphone_functions' parameter must be specified\n"
00237 "            for the node in 'rpt.conf'. Otherwise no DTMF control will be\n"
00238 "            available to the phone user.\n"
00239 "\n";
00240 
00241 static int debug = 0;  /* Set this >0 for extra debug output */
00242 static int nrpts = 0;
00243 
00244 char *discstr = "!!DISCONNECT!!";
00245 static char *remote_rig_ft897="ft897";
00246 static char *remote_rig_rbi="rbi";
00247 
00248 struct   ast_config *cfg;
00249 
00250 STANDARD_LOCAL_USER;
00251 LOCAL_USER_DECL;
00252 
00253 #define  MSWAIT 200
00254 #define  HANGTIME 5000
00255 #define  TOTIME 180000
00256 #define  IDTIME 300000
00257 #define  MAXRPTS 20
00258 #define POLITEID 30000
00259 #define FUNCTDELAY 1500
00260 
00261 static  pthread_t rpt_master_thread;
00262 
00263 struct rpt;
00264 
00265 struct rpt_link
00266 {
00267    struct rpt_link *next;
00268    struct rpt_link *prev;
00269    char  mode;       /* 1 if in tx mode */
00270    char  isremote;
00271    char  phonemode;
00272    char  name[MAXNODESTR]; /* identifier (routing) string */
00273    char  lasttx;
00274    char  lastrx;
00275    char  connected;
00276    char  hasconnected;
00277    char  outbound;
00278    char  disced;
00279    char  killme;
00280    long  elaptime;
00281    long  disctime;
00282    long  retrytimer;
00283    long  retxtimer;
00284    int   retries;
00285    struct ast_channel *chan;  
00286    struct ast_channel *pchan; 
00287 } ;
00288 
00289 struct rpt_tele
00290 {
00291    struct rpt_tele *next;
00292    struct rpt_tele *prev;
00293    struct rpt *rpt;
00294    struct ast_channel *chan;
00295    int   mode;
00296    struct rpt_link mylink;
00297    char param[TELEPARAMSIZE];
00298    pthread_t threadid;
00299 } ;
00300 
00301 struct function_table_tag
00302 {
00303    char action[ACTIONSIZE];
00304    int (*function)(struct rpt *myrpt, char *param, char *digitbuf, 
00305       int command_source, struct rpt_link *mylink);
00306 } ;
00307 
00308 /* Used to store the morse code patterns */
00309 
00310 struct morse_bits
00311 {       
00312    int len;
00313    int ddcomb;
00314 } ;
00315 
00316 struct telem_defaults
00317 {
00318    char name[20];
00319    char value[80];
00320 } ;
00321 
00322 
00323 static struct rpt
00324 {
00325    char *name;
00326    ast_mutex_t lock;
00327    char *rxchanname;
00328    char *txchanname;
00329    char *ourcontext;
00330    char *ourcallerid;
00331    char *acctcode;
00332    char *ident;
00333    char *tonezone;
00334    char *functions;
00335    char *link_functions;
00336    char *phone_functions;
00337    char *dphone_functions;
00338    char *nodes;
00339    struct rpt_link links;
00340    int hangtime;
00341    int totime;
00342    int idtime;
00343    int unkeytocttimer;
00344    char keyed;
00345    char exttx;
00346    char localtx;
00347    char remoterx;
00348    char remotetx;
00349    char remoteon;
00350    char simple;
00351    char *remote;
00352    char tounkeyed;
00353    char tonotify;
00354    char enable;
00355    char dtmfbuf[MAXDTMF];
00356    char rem_dtmfbuf[MAXDTMF];
00357    char cmdnode[50];
00358    struct ast_channel *rxchannel,*txchannel;
00359    struct ast_channel *pchannel,*txpchannel, *remchannel;
00360    struct rpt_tele tele;
00361    pthread_t rpt_call_thread,rpt_thread;
00362    time_t rem_dtmf_time,dtmf_time_rem;
00363    int tailtimer,totimer,idtimer,txconf,conf,callmode,cidx,scantimer;
00364    int mustid;
00365    int politeid;
00366    int dtmfidx,rem_dtmfidx;
00367    long  retxtimer;
00368    char mydtmf;
00369    int iobase;
00370    char exten[AST_MAX_EXTENSION];
00371    char freq[MAXREMSTR],rxpl[MAXREMSTR],txpl[MAXREMSTR];
00372    char offset;
00373    char powerlevel;
00374    char txplon;
00375    char rxplon;
00376    char remmode;
00377    char tunerequest;
00378    char hfscanmode;
00379    int hfscanstatus;
00380    char lastlinknode[MAXNODESTR];
00381    char funcchar;
00382    char endchar;
00383    char stopgen;
00384    int phone_longestfunc;
00385    int dphone_longestfunc;
00386    int link_longestfunc;
00387    int longestfunc;
00388    int longestnode;
00389    int threadrestarts;     
00390    time_t disgorgetime;
00391    time_t lastthreadrestarttime;
00392    char  nobusyout;
00393 } rpt_vars[MAXRPTS]; 
00394 
00395 /*
00396 * CLI extensions
00397 */
00398 
00399 /* Debug mode */
00400 static int rpt_do_debug(int fd, int argc, char *argv[]);
00401 
00402 static char debug_usage[] =
00403 "Usage: rpt debug level {0-7}\n"
00404 "       Enables debug messages in app_rpt\n";
00405                                                                                                                                 
00406 static struct ast_cli_entry  cli_debug =
00407         { { "rpt", "debug", "level" }, rpt_do_debug, "Enable app_rpt debugging", debug_usage };
00408 
00409 
00410 
00411 /*
00412 * Telemetry defaults
00413 */
00414 
00415 
00416 static struct telem_defaults tele_defs[] = {
00417    {"ct1","|t(350,0,100,3072)(500,0,100,3072)(660,0,100,3072)"},
00418    {"ct2","|t(660,880,150,3072)"},
00419    {"ct3","|t(440,0,150,3072)"},
00420    {"ct4","|t(550,0,150,3072)"},
00421    {"ct5","|t(660,0,150,3072)"},
00422    {"ct6","|t(880,0,150,3072)"},
00423    {"ct7","|t(660,440,150,3072)"},
00424    {"ct8","|t(700,1100,150,3072)"},
00425    {"remotemon","|t(1600,0,75,2048)"},
00426    {"remotetx","|t(2000,0,75,2048)(0,0,75,0)(1600,0,75,2048)"},
00427    {"cmdmode","|t(900,904,200,2048)"},
00428    {"functcomplete","|t(1000,0,100,2048)(0,0,100,0)(1000,0,100,2048)"}
00429 } ;
00430 
00431 /*
00432 * Forward decl's - these suppress compiler warnings when funcs coded further down the file than thier invokation
00433 */
00434 
00435 static int setrbi(struct rpt *myrpt);
00436 
00437 
00438 
00439 /*
00440 * Define function protos for function table here
00441 */
00442 
00443 static int function_ilink(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00444 static int function_autopatchup(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00445 static int function_autopatchdn(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00446 static int function_status(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00447 static int function_cop(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00448 static int function_remote(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink);
00449 /*
00450 * Function table
00451 */
00452 
00453 static struct function_table_tag function_table[] = {
00454    {"cop", function_cop},
00455    {"autopatchup", function_autopatchup},
00456    {"autopatchdn", function_autopatchdn},
00457    {"ilink", function_ilink},
00458    {"status", function_status},
00459    {"remote", function_remote}
00460 } ;
00461    
00462 static int myatoi(char *str)
00463 {
00464 int   ret;
00465 
00466    if (str == NULL) return -1;
00467    /* leave this %i alone, non-base-10 input is useful here */
00468    if (sscanf(str,"%i",&ret) != 1) return -1;
00469    return ret;
00470 }
00471 
00472 /*
00473 * Enable or disable debug output at a given level at the console
00474 */
00475                                                                                                                                  
00476 static int rpt_do_debug(int fd, int argc, char *argv[])
00477 {
00478    int newlevel;
00479 
00480         if (argc != 4)
00481                 return RESULT_SHOWUSAGE;
00482         newlevel = myatoi(argv[3]);
00483         if((newlevel < 0) || (newlevel > 7))
00484                 return RESULT_SHOWUSAGE;
00485         if(newlevel)
00486                 ast_cli(fd, "app_rpt Debugging enabled, previous level: %d, new level: %d\n", debug, newlevel);
00487         else
00488                 ast_cli(fd, "app_rpt Debugging disabled\n");
00489 
00490         debug = newlevel;                                                                                                                          
00491         return RESULT_SUCCESS;
00492 }
00493                                                                                                                                  
00494 
00495 
00496 static int play_tone_pair(struct ast_channel *chan, int f1, int f2, int duration, int amplitude)
00497 {
00498    int res;
00499 
00500         if ((res = ast_tonepair_start(chan, f1, f2, duration, amplitude)))
00501                 return res;
00502                                                                                                                                             
00503         while(chan->generatordata) {
00504       if (ast_safe_sleep(chan,1)) return -1;
00505    }
00506 
00507         return 0;
00508 }
00509 
00510 static int play_tone(struct ast_channel *chan, int freq, int duration, int amplitude)
00511 {
00512    return play_tone_pair(chan, freq, 0, duration, amplitude);
00513 }
00514 
00515 static int play_silence(struct ast_channel *chan, int duration)
00516 {
00517    return play_tone_pair(chan, 0, 0, duration, 0);
00518 }
00519 
00520 
00521 static int send_morse(struct ast_channel *chan, char *string, int speed, int freq, int amplitude)
00522 {
00523 
00524 static struct morse_bits mbits[] = {
00525       {0, 0}, /* SPACE */
00526       {0, 0}, 
00527       {6, 18},/* " */
00528       {0, 0},
00529       {7, 72},/* $ */
00530       {0, 0},
00531       {0, 0},
00532       {6, 30},/* ' */
00533       {5, 13},/* ( */
00534       {6, 29},/* ) */
00535       {0, 0},
00536       {5, 10},/* + */
00537       {6, 51},/* , */
00538       {6, 33},/* - */
00539       {6, 42},/* . */
00540       {5, 9}, /* / */
00541       {5, 31},/* 0 */
00542       {5, 30},/* 1 */
00543       {5, 28},/* 2 */
00544       {5, 24},/* 3 */
00545       {5, 16},/* 4 */
00546       {5, 0}, /* 5 */
00547       {5, 1}, /* 6 */
00548       {5, 3}, /* 7 */
00549       {5, 7}, /* 8 */
00550       {5, 15},/* 9 */
00551       {6, 7}, /* : */
00552       {6, 21},/* ; */
00553       {0, 0},
00554       {5, 33},/* = */
00555       {0, 0},
00556       {6, 12},/* ? */
00557       {0, 0},
00558          {2, 2}, /* A */
00559       {4, 1}, /* B */
00560       {4, 5}, /* C */
00561       {3, 1}, /* D */
00562       {1, 0}, /* E */
00563       {4, 4}, /* F */
00564       {3, 3}, /* G */
00565       {4, 0}, /* H */
00566       {2, 0}, /* I */
00567       {4, 14},/* J */
00568       {3, 5}, /* K */
00569       {4, 2}, /* L */
00570       {2, 3}, /* M */
00571       {2, 1}, /* N */
00572       {3, 7}, /* O */
00573       {4, 6}, /* P */
00574       {4, 11},/* Q */
00575       {3, 2}, /* R */
00576       {3, 0}, /* S */
00577       {1, 1}, /* T */
00578       {3, 4}, /* U */
00579       {4, 8}, /* V */
00580       {3, 6}, /* W */
00581       {4, 9}, /* X */
00582       {4, 13},/* Y */
00583       {4, 3}  /* Z */
00584    };
00585 
00586 
00587    int dottime;
00588    int dashtime;
00589    int intralettertime;
00590    int interlettertime;
00591    int interwordtime;
00592    int len, ddcomb;
00593    int res;
00594    int c;
00595    int i;
00596    int flags;
00597          
00598    res = 0;
00599    
00600    /* Approximate the dot time from the speed arg. */
00601    
00602    dottime = 900/speed;
00603    
00604    /* Establish timing releationships */
00605    
00606    dashtime = 3 * dottime;
00607    intralettertime = dottime;
00608    interlettertime = dottime * 4 ;
00609    interwordtime = dottime * 7;
00610    
00611    for(;(*string) && (!res); string++){
00612    
00613       c = *string;
00614       
00615       /* Convert lower case to upper case */
00616       
00617       if((c >= 'a') && (c <= 'z'))
00618          c -= 0x20;
00619       
00620       /* Can't deal with any char code greater than Z, skip it */
00621       
00622       if(c  > 'Z')
00623          continue;
00624       
00625       /* If space char, wait the inter word time */
00626                
00627       if(c == ' '){
00628          if(!res)
00629             res = play_silence(chan, interwordtime);
00630          continue;
00631       }
00632       
00633       /* Subtract out control char offset to match our table */
00634       
00635       c -= 0x20;
00636       
00637       /* Get the character data */
00638       
00639       len = mbits[c].len;
00640       ddcomb = mbits[c].ddcomb;
00641       
00642       /* Send the character */
00643       
00644       for(; len ; len--){
00645          if(!res)
00646             res = play_tone(chan, freq, (ddcomb & 1) ? dashtime : dottime, amplitude);
00647          if(!res)
00648             res = play_silence(chan, intralettertime);
00649          ddcomb >>= 1;
00650       }
00651       
00652       /* Wait the interletter time */
00653       
00654       if(!res)
00655          res = play_silence(chan, interlettertime - intralettertime);
00656    }
00657    
00658    /* Wait for all the frames to be sent */
00659    
00660    if (!res) 
00661       res = ast_waitstream(chan, "");
00662    ast_stopstream(chan);
00663    
00664    /*
00665    * Wait for the zaptel driver to physically write the tone blocks to the hardware
00666    */
00667 
00668    for(i = 0; i < 20 ; i++){
00669       flags =  ZT_IOMUX_WRITEEMPTY | ZT_IOMUX_NOWAIT; 
00670       res = ioctl(chan->fds[0], ZT_IOMUX, &flags);
00671       if(flags & ZT_IOMUX_WRITEEMPTY)
00672          break;
00673       if( ast_safe_sleep(chan, 50)){
00674          res = -1;
00675          break;
00676       }
00677    }
00678 
00679    
00680    return res;
00681 }
00682 
00683 static int send_tone_telemetry(struct ast_channel *chan, char *tonestring)
00684 {
00685    char *stringp;
00686    char *tonesubset;
00687    int f1,f2;
00688    int duration;
00689    int amplitude;
00690    int res;
00691    int i;
00692    int flags;
00693    
00694    res = 0;
00695    
00696    stringp = ast_strdupa(tonestring);
00697 
00698    for(;tonestring;){
00699       tonesubset = strsep(&stringp,")");
00700       if(!tonesubset)
00701          break;
00702       if(sscanf(tonesubset,"(%d,%d,%d,%d", &f1, &f2, &duration, &amplitude) != 4)
00703          break;
00704       res = play_tone_pair(chan, f1, f2, duration, amplitude);
00705       if(res)
00706          break;
00707    }
00708    if(!res)
00709       res = play_tone_pair(chan, 0, 0, 100, 0); /* This is needed to ensure the last tone segment is timed correctly */
00710    
00711    if (!res) 
00712       res = ast_waitstream(chan, "");
00713    ast_stopstream(chan);
00714 
00715    /*
00716    * Wait for the zaptel driver to physically write the tone blocks to the hardware
00717    */
00718 
00719    for(i = 0; i < 20 ; i++){
00720       flags =  ZT_IOMUX_WRITEEMPTY | ZT_IOMUX_NOWAIT; 
00721       res = ioctl(chan->fds[0], ZT_IOMUX, &flags);
00722       if(flags & ZT_IOMUX_WRITEEMPTY)
00723          break;
00724       if( ast_safe_sleep(chan, 50)){
00725          res = -1;
00726          break;
00727       }
00728    }
00729       
00730    return res;
00731       
00732 }
00733    
00734 
00735 static int sayfile(struct ast_channel *mychannel,char *fname)
00736 {
00737 int   res;
00738 
00739    res = ast_streamfile(mychannel, fname, mychannel->language);
00740    if (!res) 
00741       res = ast_waitstream(mychannel, "");
00742    else
00743        ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
00744    ast_stopstream(mychannel);
00745    return res;
00746 }
00747 
00748 static int saycharstr(struct ast_channel *mychannel,char *str)
00749 {
00750 int   res;
00751 
00752    res = ast_say_character_str(mychannel,str,NULL,mychannel->language);
00753    if (!res) 
00754       res = ast_waitstream(mychannel, "");
00755    else
00756        ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
00757    ast_stopstream(mychannel);
00758    return res;
00759 }
00760 
00761 static int saynum(struct ast_channel *mychannel, int num)
00762 {
00763    int res;
00764    res = ast_say_number(mychannel, num, NULL, mychannel->language, NULL);
00765    if(!res)
00766       res = ast_waitstream(mychannel, "");
00767    else
00768       ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
00769    ast_stopstream(mychannel);
00770    return res;
00771 }
00772 
00773 
00774 /* Retrieve an int from a config file */
00775                                                                                 
00776 static int retrieve_astcfgint(char *category, char *name, int min, int max, int defl)
00777 {
00778         char *var;
00779         int ret;
00780                                                                                 
00781         var = ast_variable_retrieve(cfg, category, name);
00782         if(var){
00783                 ret = myatoi(var);
00784                 if(ret < min)
00785                         ret = min;
00786                 if(ret > max)
00787                         ret = max;
00788         }
00789         else
00790                 ret = defl;
00791         return ret;
00792 }
00793 
00794 static int telem_any(struct ast_channel *chan, char *entry)
00795 {
00796    int res;
00797    char c;
00798    
00799    static int morsespeed;
00800    static int morsefreq;
00801    static int morseampl;
00802    static int morseidfreq = 0;
00803    static int morseidampl;
00804    static char mcat[] = MORSE;
00805    
00806    res = 0;
00807    
00808    if(!morseidfreq){ /* Get the morse parameters if not already loaded */
00809       morsespeed = retrieve_astcfgint( mcat, "speed", 5, 20, 20);
00810          morsefreq = retrieve_astcfgint( mcat, "frequency", 300, 3000, 800);
00811          morseampl = retrieve_astcfgint( mcat, "amplitude", 200, 8192, 4096);
00812       morseidampl = retrieve_astcfgint( mcat, "idamplitude", 200, 8192, 2048);
00813       morseidfreq = retrieve_astcfgint( mcat, "idfrequency", 300, 3000, 330); 
00814    }
00815    
00816    /* Is it a file, or a tone sequence? */
00817          
00818    if(entry[0] == '|'){
00819       c = entry[1];
00820       if((c >= 'a')&&(c <= 'z'))
00821          c -= 0x20;
00822    
00823       switch(c){
00824          case 'I': /* Morse ID */
00825             res = send_morse(chan, entry + 2, morsespeed, morseidfreq, morseidampl);
00826             break;
00827          
00828          case 'M': /* Morse Message */
00829             res = send_morse(chan, entry + 2, morsespeed, morsefreq, morseampl);
00830             break;
00831          
00832          case 'T': /* Tone sequence */
00833             res = send_tone_telemetry(chan, entry + 2);
00834             break;
00835          default:
00836             res = -1;
00837       }
00838    }
00839    else
00840       res = sayfile(chan, entry); /* File */
00841    return res;
00842 }
00843 
00844 /*
00845 * This function looks up a telemetry name in the config file, and does a telemetry response as configured.
00846 *
00847 * 4 types of telemtry are handled: Morse ID, Morse Message, Tone Sequence, and a File containing a recording.
00848 */
00849 
00850 static int telem_lookup(struct ast_channel *chan, char *node, char *name)
00851 {
00852    
00853    int res;
00854    int i;
00855    char *entry;
00856    char *telemetry;
00857    char *telemetry_save;
00858 
00859    res = 0;
00860    telemetry_save = NULL;
00861    entry = NULL;
00862    
00863    
00864    /* Retrieve the section name for telemetry from the node section */
00865    
00866    telemetry = ast_variable_retrieve(cfg, node, TELEMETRY);
00867    if(telemetry){
00868       telemetry_save = ast_strdupa(telemetry);
00869       if(!telemetry_save){
00870          ast_log(LOG_WARNING,"ast_strdupa() failed in telem_lookup()\n");
00871          return res;
00872       }
00873       entry = ast_variable_retrieve(cfg, telemetry_save, name);
00874    }
00875    
00876    /* Try to look up the telemetry name */
00877    
00878    if(!entry){
00879       /* Telemetry name wasn't found in the config file, use the default */
00880       for(i = 0; i < sizeof(tele_defs)/sizeof(struct telem_defaults) ; i++){
00881          if(!strcasecmp(tele_defs[i].name, name))
00882             entry = tele_defs[i].value;
00883       }
00884    }
00885    if(entry)   
00886       telem_any(chan, entry);
00887    else{
00888       ast_log(LOG_WARNING, "Telemetry name not found: %s\n", name);
00889       res = -1;
00890    }
00891    return res;
00892 }
00893 
00894 /*
00895 * Retrieve a wait interval
00896 */
00897 
00898 static int get_wait_interval(struct rpt *myrpt, int type)
00899 {
00900         int interval;
00901         char *wait_times;
00902         char *wait_times_save;
00903                                                                                                                   
00904         wait_times_save = NULL;
00905         wait_times = ast_variable_retrieve(cfg, myrpt->name, "wait_times");
00906                                                                                                                   
00907         if(wait_times){
00908                 wait_times_save = ast_strdupa(wait_times);
00909                 if(!wait_times_save){
00910                         ast_log(LOG_WARNING, "Out of memory in wait_interval()\n");
00911                         wait_times = NULL;
00912                 }
00913         }
00914                                                                                                                   
00915         switch(type){
00916                 case DLY_TELEM:
00917                         if(wait_times)
00918                                 interval = retrieve_astcfgint(wait_times_save, "telemwait", 500, 5000, 1000);
00919                         else
00920                                 interval = 1000;
00921                         break;
00922                                                                                                                   
00923                 case DLY_ID:
00924                         if(wait_times)
00925                                 interval = retrieve_astcfgint(wait_times_save, "idwait",250,5000,500);
00926                         else
00927                                 interval = 500;
00928                         break;
00929                                                                                                                   
00930                 case DLY_UNKEY:
00931                         if(wait_times)
00932                                 interval = retrieve_astcfgint(wait_times_save, "unkeywait",500,5000,1000);
00933                         else
00934                                 interval = 1000;
00935                         break;
00936                                                                                                                   
00937                 case DLY_CALLTERM:
00938                         if(wait_times)
00939                                 interval = retrieve_astcfgint(wait_times_save, "calltermwait",500,5000,1500);
00940                         else
00941                                 interval = 1500;
00942                         break;
00943                                                                                                                   
00944                 default:
00945                         return 0;
00946         }
00947    return interval;
00948 }                                                                                                                  
00949 
00950 
00951 /*
00952 * Wait a configurable interval of time 
00953 */
00954 
00955 
00956 static void wait_interval(struct rpt *myrpt, int type, struct ast_channel *chan)
00957 {
00958    int interval;
00959    if((interval = get_wait_interval(myrpt, type)))
00960       ast_safe_sleep(chan,interval);
00961    return;
00962 }
00963 
00964 
00965 static void *rpt_tele_thread(void *this)
00966 {
00967 ZT_CONFINFO ci;  /* conference info */
00968 int   res = 0,haslink,hastx,hasremote,imdone = 0, unkeys_queued, x;
00969 struct   rpt_tele *mytele = (struct rpt_tele *)this;
00970 struct  rpt_tele *tlist;
00971 struct   rpt *myrpt;
00972 struct   rpt_link *l,*m,linkbase;
00973 struct   ast_channel *mychannel;
00974 int vmajor, vminor;
00975 char *p,*ct,*ct_copy,*ident, *nodename;
00976 time_t t;
00977 struct tm localtm;
00978 
00979 
00980    /* get a pointer to myrpt */
00981    myrpt = mytele->rpt;
00982 
00983    /* Snag copies of a few key myrpt variables */
00984    ast_mutex_lock(&myrpt->lock);
00985    nodename = ast_strdupa(myrpt->name);
00986    ident = ast_strdupa(myrpt->ident);
00987    ast_mutex_unlock(&myrpt->lock);
00988    
00989    
00990    /* allocate a pseudo-channel thru asterisk */
00991    mychannel = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
00992    if (!mychannel)
00993    {
00994       fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
00995       ast_mutex_lock(&myrpt->lock);
00996       remque((struct qelem *)mytele);
00997       ast_mutex_unlock(&myrpt->lock);
00998       free(mytele);     
00999       pthread_exit(NULL);
01000    }
01001    ast_mutex_lock(&myrpt->lock);
01002    mytele->chan = mychannel; /* Save a copy of the channel so we can access it externally if need be */
01003    ast_mutex_unlock(&myrpt->lock);
01004    
01005    /* make a conference for the tx */
01006    ci.chan = 0;
01007    /* If there's an ID queued, only connect the ID audio to the local tx conference so 
01008       linked systems can't hear it */
01009    ci.confno = (((mytele->mode == ID) || (mytele->mode == IDTALKOVER) || (mytele->mode == UNKEY)) ?
01010        myrpt->txconf : myrpt->conf);
01011    ci.confmode = ZT_CONF_CONFANN;
01012    /* first put the channel on the conference in announce mode */
01013    if (ioctl(mychannel->fds[0],ZT_SETCONF,&ci) == -1)
01014    {
01015       ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
01016       ast_mutex_lock(&myrpt->lock);
01017       remque((struct qelem *)mytele);
01018       ast_mutex_unlock(&myrpt->lock);
01019       free(mytele);     
01020       ast_hangup(mychannel);
01021       pthread_exit(NULL);
01022    }
01023    ast_stopstream(mychannel);
01024    switch(mytele->mode)
01025    {
01026        case ID:
01027        case ID1:
01028       /* wait a bit */
01029       wait_interval(myrpt, (mytele->mode == ID) ? DLY_ID : DLY_TELEM,mychannel);
01030       res = telem_any(mychannel, ident); 
01031       imdone=1;
01032    
01033       break;
01034       
01035       
01036        case IDTALKOVER:
01037          p = ast_variable_retrieve(cfg, nodename, "idtalkover");
01038          if(p)
01039          res = telem_any(mychannel, p); 
01040       imdone=1;   
01041          break;
01042             
01043        case PROC:
01044       /* wait a little bit longer */
01045       wait_interval(myrpt, DLY_TELEM, mychannel);
01046       res = ast_streamfile(mychannel, "rpt/callproceeding", mychannel->language);
01047       break;
01048        case TERM:
01049       /* wait a little bit longer */
01050       wait_interval(myrpt, DLY_CALLTERM, mychannel);
01051       res = ast_streamfile(mychannel, "rpt/callterminated", mychannel->language);
01052       break;
01053        case COMPLETE:
01054       /* wait a little bit */
01055       wait_interval(myrpt, DLY_TELEM, mychannel);
01056       res = telem_lookup(mychannel, myrpt->name, "functcomplete");
01057       break;
01058        case UNKEY:
01059 
01060       /*
01061       * Reset the Unkey to CT timer
01062       */
01063 
01064       x = get_wait_interval(myrpt, DLY_UNKEY);
01065       ast_mutex_lock(&myrpt->lock);
01066       myrpt->unkeytocttimer = x; /* Must be protected as it is changed below */
01067       ast_mutex_unlock(&myrpt->lock);
01068 
01069       /*
01070       * If there's one already queued, don't do another
01071       */
01072 
01073       tlist = myrpt->tele.next;
01074       unkeys_queued = 0;
01075                 if (tlist != &myrpt->tele)
01076                 {
01077                         ast_mutex_lock(&myrpt->lock);
01078                         while(tlist != &myrpt->tele){
01079                                 if (tlist->mode == UNKEY) unkeys_queued++;
01080                                 tlist = tlist->next;
01081                         }
01082                         ast_mutex_unlock(&myrpt->lock);
01083       }
01084       if( unkeys_queued > 1){
01085          imdone = 1;
01086          break;
01087       }
01088 
01089       /* Wait for the telemetry timer to expire */
01090       /* Periodically check the timer since it can be re-initialized above */
01091 
01092       while(myrpt->unkeytocttimer)
01093       {
01094          int ctint;
01095          if(myrpt->unkeytocttimer > 100)
01096             ctint = 100;
01097          else
01098             ctint = myrpt->unkeytocttimer;
01099          ast_safe_sleep(mychannel, ctint);
01100          ast_mutex_lock(&myrpt->lock);
01101          if(myrpt->unkeytocttimer < ctint)
01102             myrpt->unkeytocttimer = 0;
01103          else
01104             myrpt->unkeytocttimer -= ctint;
01105          ast_mutex_unlock(&myrpt->lock);
01106       }
01107    
01108 
01109       /*
01110       * Now, the carrier on the rptr rx should be gone. 
01111       * If it re-appeared, then forget about sending the CT
01112       */
01113       if(myrpt->keyed){
01114          imdone = 1;
01115          break;
01116       }
01117          
01118       haslink = 0;
01119       hastx = 0;
01120       hasremote = 0;    
01121       l = myrpt->links.next;
01122       if (l != &myrpt->links)
01123       {
01124          ast_mutex_lock(&myrpt->lock);
01125          while(l != &myrpt->links)
01126          {
01127             if (l->name[0] == '0')
01128             {
01129                l = l->next;
01130                continue;
01131             }
01132             haslink = 1;
01133             if (l->mode) {
01134                hastx++;
01135                if (l->isremote) hasremote++;
01136             }
01137             l = l->next;
01138          }
01139          ast_mutex_unlock(&myrpt->lock);
01140       }
01141       if (haslink)
01142       {
01143 
01144          res = telem_lookup(mychannel, myrpt->name, (!hastx) ? "remotemon" : "remotetx");
01145          if(res)
01146             ast_log(LOG_WARNING, "telem_lookup:remotexx failed on %s\n", mychannel->name);
01147          
01148       
01149          /* if in remote cmd mode, indicate it */
01150          if (myrpt->cmdnode[0])
01151          {
01152             ast_safe_sleep(mychannel,200);
01153             res = telem_lookup(mychannel, myrpt->name, "cmdmode");
01154             if(res)
01155                ast_log(LOG_WARNING, "telem_lookup:cmdmode failed on %s\n", mychannel->name);
01156             ast_stopstream(mychannel);
01157          }
01158       }
01159       else if((ct = ast_variable_retrieve(cfg, nodename, "unlinkedct"))){ /* Unlinked Courtesy Tone */
01160          ct_copy = ast_strdupa(ct);
01161          res = telem_lookup(mychannel, myrpt->name, ct_copy);
01162          if(res)
01163             ast_log(LOG_WARNING, "telem_lookup:ctx failed on %s\n", mychannel->name);     
01164       }  
01165          
01166       if (hasremote && (!myrpt->cmdnode[0]))
01167       {
01168          /* set for all to hear */
01169          ci.chan = 0;
01170          ci.confno = myrpt->conf;
01171          ci.confmode = ZT_CONF_CONFANN;
01172          /* first put the channel on the conference in announce mode */
01173          if (ioctl(mychannel->fds[0],ZT_SETCONF,&ci) == -1)
01174          {
01175             ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
01176             ast_mutex_lock(&myrpt->lock);
01177             remque((struct qelem *)mytele);
01178             ast_mutex_unlock(&myrpt->lock);
01179             free(mytele);     
01180             ast_hangup(mychannel);
01181             pthread_exit(NULL);
01182          }
01183          if((ct = ast_variable_retrieve(cfg, nodename, "remotect"))){ /* Unlinked Courtesy Tone */
01184             ast_safe_sleep(mychannel,200);
01185             ct_copy = ast_strdupa(ct);
01186             res = telem_lookup(mychannel, myrpt->name, ct_copy);
01187             if(res)
01188                ast_log(LOG_WARNING, "telem_lookup:ctx failed on %s\n", mychannel->name);     
01189          }  
01190       }
01191       imdone = 1;
01192       break;
01193        case REMDISC:
01194       /* wait a little bit */
01195       wait_interval(myrpt, DLY_TELEM, mychannel);
01196       res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01197       if (!res) 
01198          res = ast_waitstream(mychannel, "");
01199       else
01200           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01201       ast_stopstream(mychannel);
01202       ast_say_character_str(mychannel,mytele->mylink.name,NULL,mychannel->language);
01203       res = ast_streamfile(mychannel, ((mytele->mylink.connected) ? 
01204          "rpt/remote_disc" : "rpt/remote_busy"), mychannel->language);
01205       break;
01206        case REMALREADY:
01207       /* wait a little bit */
01208       wait_interval(myrpt, DLY_TELEM, mychannel);
01209       res = ast_streamfile(mychannel, "rpt/remote_already", mychannel->language);
01210       break;
01211        case REMNOTFOUND:
01212       /* wait a little bit */
01213       wait_interval(myrpt, DLY_TELEM, mychannel);
01214       res = ast_streamfile(mychannel, "rpt/remote_notfound", mychannel->language);
01215       break;
01216        case REMGO:
01217       /* wait a little bit */
01218       wait_interval(myrpt, DLY_TELEM, mychannel);
01219       res = ast_streamfile(mychannel, "rpt/remote_go", mychannel->language);
01220       break;
01221        case CONNECTED:
01222       /* wait a little bit */
01223       wait_interval(myrpt, DLY_TELEM,  mychannel);
01224       res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01225       if (!res) 
01226          res = ast_waitstream(mychannel, "");
01227       else
01228           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01229       ast_stopstream(mychannel);
01230       ast_say_character_str(mychannel,mytele->mylink.name,NULL,mychannel->language);
01231       res = ast_streamfile(mychannel, "rpt/connected", mychannel->language);
01232       break;
01233        case CONNFAIL:
01234       res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01235       if (!res) 
01236          res = ast_waitstream(mychannel, "");
01237       else
01238           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01239       ast_stopstream(mychannel);
01240       ast_say_character_str(mychannel,mytele->mylink.name,NULL,mychannel->language);
01241       res = ast_streamfile(mychannel, "rpt/connection_failed", mychannel->language);
01242       break;
01243        case STATUS:
01244       /* wait a little bit */
01245       wait_interval(myrpt, DLY_TELEM, mychannel);
01246       hastx = 0;
01247       linkbase.next = &linkbase;
01248       linkbase.prev = &linkbase;
01249       ast_mutex_lock(&myrpt->lock);
01250       /* make our own list of links */
01251       l = myrpt->links.next;
01252       while(l != &myrpt->links)
01253       {
01254          if (l->name[0] == '0')
01255          {
01256             l = l->next;
01257             continue;
01258          }
01259          m = malloc(sizeof(struct rpt_link));
01260          if (!m)
01261          {
01262             ast_log(LOG_WARNING, "Cannot alloc memory on %s\n", mychannel->name);
01263             ast_mutex_lock(&myrpt->lock);
01264             remque((struct qelem *)mytele);
01265             ast_mutex_unlock(&myrpt->lock);
01266             free(mytele);     
01267             ast_hangup(mychannel);
01268             pthread_exit(NULL);
01269          }
01270          memcpy(m,l,sizeof(struct rpt_link));
01271          m->next = m->prev = NULL;
01272          insque((struct qelem *)m,(struct qelem *)linkbase.next);
01273          l = l->next;
01274       }
01275       ast_mutex_unlock(&myrpt->lock);
01276       res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01277       if (!res) 
01278          res = ast_waitstream(mychannel, "");
01279       else
01280           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01281       ast_stopstream(mychannel);
01282       ast_say_character_str(mychannel,myrpt->name,NULL,mychannel->language);
01283       if (!res) 
01284          res = ast_waitstream(mychannel, "");
01285       else
01286           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01287       ast_stopstream(mychannel);
01288       if (myrpt->callmode)
01289       {
01290          hastx = 1;
01291          res = ast_streamfile(mychannel, "rpt/autopatch_on", mychannel->language);
01292          if (!res) 
01293             res = ast_waitstream(mychannel, "");
01294          else
01295              ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01296          ast_stopstream(mychannel);
01297       }
01298       l = linkbase.next;
01299       while(l != &linkbase)
01300       {
01301          hastx = 1;
01302          res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01303          if (!res) 
01304             res = ast_waitstream(mychannel, "");
01305          else
01306             ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01307          ast_stopstream(mychannel);
01308          ast_say_character_str(mychannel,l->name,NULL,mychannel->language);
01309          if (!res) 
01310             res = ast_waitstream(mychannel, "");
01311          else
01312              ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01313          ast_stopstream(mychannel);
01314          res = ast_streamfile(mychannel, ((l->mode) ? 
01315             "rpt/tranceive" : "rpt/monitor"), mychannel->language);
01316          if (!res) 
01317             res = ast_waitstream(mychannel, "");
01318          else
01319             ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01320          ast_stopstream(mychannel);
01321          l = l->next;
01322       }        
01323       if (!hastx)
01324       {
01325          res = ast_streamfile(mychannel, "rpt/repeat_only", mychannel->language);
01326          if (!res) 
01327             res = ast_waitstream(mychannel, "");
01328          else
01329              ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01330          ast_stopstream(mychannel);
01331       }
01332       /* destroy our local link queue */
01333       l = linkbase.next;
01334       while(l != &linkbase)
01335       {
01336          m = l;
01337          l = l->next;
01338          remque((struct qelem *)m);
01339          free(m);
01340       }        
01341       imdone = 1;
01342       break;
01343        case TIMEOUT:
01344       res = ast_streamfile(mychannel, "rpt/node", mychannel->language);
01345       if (!res) 
01346          res = ast_waitstream(mychannel, "");
01347       else
01348           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01349       ast_stopstream(mychannel);
01350       ast_say_character_str(mychannel,myrpt->name,NULL,mychannel->language);
01351       res = ast_streamfile(mychannel, "rpt/timeout", mychannel->language);
01352       break;
01353       
01354        case STATS_TIME:
01355          wait_interval(myrpt, DLY_TELEM, mychannel); /* Wait a little bit */
01356       t = time(NULL);
01357       localtime_r(&t, &localtm);
01358       /* Say the phase of the day is before the time */
01359       if((localtm.tm_hour >= 0) && (localtm.tm_hour < 12))
01360          p = "rpt/goodmorning";
01361       else if((localtm.tm_hour >= 12) && (localtm.tm_hour < 18))
01362          p = "rpt/goodafternoon";
01363       else
01364          p = "rpt/goodevening";
01365       if (sayfile(mychannel,p) == -1)
01366       {
01367          imdone = 1;
01368          break;
01369       }
01370       /* Say the time is ... */     
01371       if (sayfile(mychannel,"rpt/thetimeis") == -1)
01372       {
01373          imdone = 1;
01374          break;
01375       }
01376       /* Say the time */            
01377          res = ast_say_time(mychannel, t, "", mychannel->language);
01378       if (!res) 
01379          res = ast_waitstream(mychannel, "");
01380       ast_stopstream(mychannel);    
01381       imdone = 1;
01382          break;
01383        case STATS_VERSION:
01384       p = strstr(tdesc, "version"); 
01385       if(!p)
01386          break;   
01387       if(sscanf(p, "version %d.%d", &vmajor, &vminor) != 2)
01388          break;
01389          wait_interval(myrpt, DLY_TELEM, mychannel); /* Wait a little bit */
01390       /* Say "version" */
01391       if (sayfile(mychannel,"rpt/version") == -1)
01392       {
01393          imdone = 1;
01394          break;
01395       }
01396       if(!res) /* Say "X" */
01397          ast_say_number(mychannel, vmajor, "", mychannel->language, (char *) NULL);
01398       if (!res) 
01399          res = ast_waitstream(mychannel, "");
01400       ast_stopstream(mychannel); 
01401       if (saycharstr(mychannel,".") == -1)
01402       {
01403          imdone = 1;
01404          break;
01405       }
01406       if(!res) /* Say "Y" */
01407          ast_say_number(mychannel, vminor, "", mychannel->language, (char *) NULL);
01408       if (!res){
01409          res = ast_waitstream(mychannel, "");
01410          ast_stopstream(mychannel);
01411       }  
01412       else
01413           ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01414       imdone = 1;
01415          break;
01416        case ARB_ALPHA:
01417          wait_interval(myrpt, DLY_TELEM, mychannel); /* Wait a little bit */
01418          if(mytele->param)
01419             saycharstr(mychannel, mytele->param);
01420          imdone = 1;
01421       break;
01422        case REV_PATCH:
01423          wait_interval(myrpt, DLY_TELEM, mychannel); /* Wait a little bit */
01424          if(mytele->param) {
01425 
01426          /* Parts of this section taken from app_parkandannounce */
01427          char *tpl_working, *tpl_current;
01428          char *tmp[100], *myparm;
01429          int looptemp=0,i=0, dres = 0;
01430    
01431 
01432          tpl_working = strdupa(mytele->param);
01433          myparm = strsep(&tpl_working,",");
01434          tpl_current=strsep(&tpl_working, ":");
01435 
01436          while(tpl_current && looptemp < sizeof(tmp)) {
01437             tmp[looptemp]=tpl_current;
01438             looptemp++;
01439             tpl_current=strsep(&tpl_working,":");
01440          }
01441 
01442          for(i=0; i<looptemp; i++) {
01443             if(!strcmp(tmp[i], "PARKED")) {
01444                ast_say_digits(mychannel, atoi(myparm), "", mychannel->language);
01445             } else if(!strcmp(tmp[i], "NODE")) {
01446                ast_say_digits(mychannel, atoi(myrpt->name), "", mychannel->language);
01447             } else {
01448                dres = ast_streamfile(mychannel, tmp[i], mychannel->language);
01449                if(!dres) {
01450                   dres = ast_waitstream(mychannel, "");
01451                } else {
01452                   ast_log(LOG_WARNING, "ast_streamfile of %s failed on %s\n", tmp[i], mychannel->name);
01453                   dres = 0;
01454                }
01455             }
01456          }
01457       }
01458          imdone = 1;
01459       break;
01460        case TEST_TONE:
01461       imdone = 1;
01462       myrpt->stopgen = 0;
01463            if ((res = ast_tonepair_start(mychannel, 1004.0, 0, 99999999, 7200.0))) 
01464          break;
01465            while(mychannel->generatordata && (!myrpt->stopgen)) {
01466          if (ast_safe_sleep(mychannel,1)) break;
01467             imdone = 1;
01468          }
01469       break;
01470        default:
01471          break;
01472    }
01473    myrpt->stopgen = 0;
01474    if (!imdone)
01475    {
01476       if (!res) 
01477          res = ast_waitstream(mychannel, "");
01478       else {
01479          ast_log(LOG_WARNING, "ast_streamfile failed on %s\n", mychannel->name);
01480          res = 0;
01481       }
01482    }
01483    ast_stopstream(mychannel);
01484    ast_mutex_lock(&myrpt->lock);
01485    remque((struct qelem *)mytele);
01486    ast_mutex_unlock(&myrpt->lock);
01487    free(mytele);     
01488    ast_hangup(mychannel);
01489    pthread_exit(NULL);
01490 }
01491 
01492 static void rpt_telemetry(struct rpt *myrpt,int mode, void *data)
01493 {
01494 struct rpt_tele *tele;
01495 struct rpt_link *mylink = (struct rpt_link *) data;
01496 pthread_attr_t attr;
01497 
01498    tele = malloc(sizeof(struct rpt_tele));
01499    if (!tele)
01500    {
01501       ast_log(LOG_WARNING, "Unable to allocate memory\n");
01502       pthread_exit(NULL);
01503       return;
01504    }
01505    /* zero it out */
01506    memset((char *)tele,0,sizeof(struct rpt_tele));
01507    tele->rpt = myrpt;
01508    tele->mode = mode;
01509    ast_mutex_lock(&myrpt->lock);
01510    if((mode == CONNFAIL) || (mode == REMDISC) || (mode == CONNECTED)){
01511       memset(&tele->mylink,0,sizeof(struct rpt_link));
01512       if (mylink){
01513          memcpy(&tele->mylink,mylink,sizeof(struct rpt_link));
01514       }
01515    }
01516    else if ((mode == ARB_ALPHA) || (mode == REV_PATCH)) {
01517       strncpy(tele->param, (char *) data, TELEPARAMSIZE - 1);
01518       tele->param[TELEPARAMSIZE - 1] = 0;
01519    }
01520    insque((struct qelem *)tele,(struct qelem *)myrpt->tele.next); 
01521    ast_mutex_unlock(&myrpt->lock);
01522         pthread_attr_init(&attr);
01523         pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
01524    ast_pthread_create(&tele->threadid,&attr,rpt_tele_thread,(void *) tele);
01525    return;
01526 }
01527 
01528 static void *rpt_call(void *this)
01529 {
01530 ZT_CONFINFO ci;  /* conference info */
01531 struct   rpt *myrpt = (struct rpt *)this;
01532 int   res;
01533 struct   ast_frame wf;
01534 int stopped,congstarted;
01535 struct ast_channel *mychannel,*genchannel;
01536 
01537    myrpt->mydtmf = 0;
01538    /* allocate a pseudo-channel thru asterisk */
01539    mychannel = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
01540    if (!mychannel)
01541    {
01542       fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
01543       pthread_exit(NULL);
01544    }
01545    ci.chan = 0;
01546    ci.confno = myrpt->conf; /* use the pseudo conference */
01547    ci.confmode = ZT_CONF_REALANDPSEUDO | ZT_CONF_TALKER | ZT_CONF_LISTENER
01548       | ZT_CONF_PSEUDO_TALKER | ZT_CONF_PSEUDO_LISTENER; 
01549    /* first put the channel on the conference */
01550    if (ioctl(mychannel->fds[0],ZT_SETCONF,&ci) == -1)
01551    {
01552       ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
01553       ast_hangup(mychannel);
01554       myrpt->callmode = 0;
01555       pthread_exit(NULL);
01556    }
01557    /* allocate a pseudo-channel thru asterisk */
01558    genchannel = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
01559    if (!genchannel)
01560    {
01561       fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
01562       ast_hangup(mychannel);
01563       pthread_exit(NULL);
01564    }
01565    ci.chan = 0;
01566    ci.confno = myrpt->conf;
01567    ci.confmode = ZT_CONF_REALANDPSEUDO | ZT_CONF_TALKER | ZT_CONF_LISTENER
01568       | ZT_CONF_PSEUDO_TALKER | ZT_CONF_PSEUDO_LISTENER; 
01569    /* first put the channel on the conference */
01570    if (ioctl(genchannel->fds[0],ZT_SETCONF,&ci) == -1)
01571    {
01572       ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
01573       ast_hangup(mychannel);
01574       ast_hangup(genchannel);
01575       myrpt->callmode = 0;
01576       pthread_exit(NULL);
01577    }
01578    if (myrpt->tonezone && (tone_zone_set_zone(mychannel->fds[0],myrpt->tonezone) == -1))
01579    {
01580       ast_log(LOG_WARNING, "Unable to set tone zone %s\n",myrpt->tonezone);
01581       ast_hangup(mychannel);
01582       ast_hangup(genchannel);
01583       myrpt->callmode = 0;
01584       pthread_exit(NULL);
01585    }
01586    if (myrpt->tonezone && (tone_zone_set_zone(genchannel->fds[0],myrpt->tonezone) == -1))
01587    {
01588       ast_log(LOG_WARNING, "Unable to set tone zone %s\n",myrpt->tonezone);
01589       ast_hangup(mychannel);
01590       ast_hangup(genchannel);
01591       myrpt->callmode = 0;
01592       pthread_exit(NULL);
01593    }
01594    /* start dialtone */
01595    if (tone_zone_play_tone(mychannel->fds[0],ZT_TONE_DIALTONE) < 0)
01596    {
01597       ast_log(LOG_WARNING, "Cannot start dialtone\n");
01598       ast_hangup(mychannel);
01599       ast_hangup(genchannel);
01600       myrpt->callmode = 0;
01601       pthread_exit(NULL);
01602    }
01603    stopped = 0;
01604    congstarted = 0;
01605    while ((myrpt->callmode == 1) || (myrpt->callmode == 4))
01606    {
01607 
01608       if ((myrpt->callmode == 1) && (myrpt->cidx > 0) && (!stopped))
01609       {
01610          stopped = 1;
01611          /* stop dial tone */
01612          tone_zone_play_tone(mychannel->fds[0],-1);
01613       }
01614       if ((myrpt->callmode == 4) && (!congstarted))
01615       {
01616          congstarted = 1;
01617          /* start congestion tone */
01618          tone_zone_play_tone(mychannel->fds[0],ZT_TONE_CONGESTION);
01619       }
01620       res = ast_safe_sleep(mychannel, MSWAIT);
01621       if (res < 0)
01622       {
01623          ast_hangup(mychannel);
01624          ast_hangup(genchannel);
01625          ast_mutex_lock(&myrpt->lock);
01626          myrpt->callmode = 0;
01627          ast_mutex_unlock(&myrpt->lock);
01628          pthread_exit(NULL);
01629       }
01630    }
01631    /* stop any tone generation */
01632    tone_zone_play_tone(mychannel->fds[0],-1);
01633    /* end if done */
01634    if (!myrpt->callmode)
01635    {
01636       ast_hangup(mychannel);
01637       ast_hangup(genchannel);
01638       ast_mutex_lock(&myrpt->lock);
01639       myrpt->callmode = 0;
01640       ast_mutex_unlock(&myrpt->lock);
01641       pthread_exit(NULL);        
01642    }
01643 
01644    if (myrpt->ourcallerid && *myrpt->ourcallerid){
01645       char *name, *loc, *instr;
01646       instr = strdup(myrpt->ourcallerid);
01647       if(instr){
01648          ast_callerid_parse(instr, &name, &loc);
01649          if(loc){
01650             if(mychannel->cid.cid_num)
01651                free(mychannel->cid.cid_num);
01652             mychannel->cid.cid_num = strdup(loc);
01653          }
01654          if(name){
01655             if(mychannel->cid.cid_name)
01656                free(mychannel->cid.cid_name);
01657             mychannel->cid.cid_name = strdup(name);
01658          }
01659          free(instr);
01660       }
01661    }
01662 
01663    strncpy(mychannel->exten, myrpt->exten, sizeof(mychannel->exten) - 1);
01664    strncpy(mychannel->context, myrpt->ourcontext, sizeof(mychannel->context) - 1);
01665    if (myrpt->acctcode)
01666       strncpy(mychannel->accountcode, myrpt->acctcode, sizeof(mychannel->accountcode) - 1);
01667    mychannel->priority = 1;
01668    ast_channel_undefer_dtmf(mychannel);
01669    if (ast_pbx_start(mychannel) < 0)
01670    {
01671       ast_log(LOG_WARNING, "Unable to start PBX!!\n");
01672       ast_hangup(mychannel);
01673       ast_hangup(genchannel);
01674       ast_mutex_lock(&myrpt->lock);
01675       myrpt->callmode = 0;
01676       ast_mutex_unlock(&myrpt->lock);
01677       pthread_exit(NULL);
01678    }
01679    usleep(10000);
01680    ast_mutex_lock(&myrpt->lock);
01681    myrpt->callmode = 3;
01682    while(myrpt->callmode)
01683    {
01684       if ((!mychannel->pbx) && (myrpt->callmode != 4))
01685       {
01686          myrpt->callmode = 4;
01687          ast_mutex_unlock(&myrpt->lock);
01688          /* start congestion tone */
01689          tone_zone_play_tone(genchannel->fds[0],ZT_TONE_CONGESTION);
01690          ast_mutex_lock(&myrpt->lock);
01691       }
01692       if (myrpt->mydtmf)
01693       {
01694          wf.frametype = AST_FRAME_DTMF;
01695          wf.subclass = myrpt->mydtmf;
01696          wf.offset = 0;
01697          wf.mallocd = 0;
01698          wf.data = NULL;
01699          wf.datalen = 0;
01700          wf.samples = 0;
01701          ast_mutex_unlock(&myrpt->lock);
01702          ast_write(genchannel,&wf); 
01703          ast_mutex_lock(&myrpt->lock);
01704          myrpt->mydtmf = 0;
01705       }
01706       ast_mutex_unlock(&myrpt->lock);
01707       usleep(MSWAIT * 1000);
01708       ast_mutex_lock(&myrpt->lock);
01709    }
01710    ast_mutex_unlock(&myrpt->lock);
01711    tone_zone_play_tone(genchannel->fds[0],-1);
01712    if (mychannel->pbx) ast_softhangup(mychannel,AST_SOFTHANGUP_DEV);
01713    ast_hangup(genchannel);
01714    ast_mutex_lock(&myrpt->lock);
01715    myrpt->callmode = 0;
01716    ast_mutex_unlock(&myrpt->lock);
01717    pthread_exit(NULL);
01718 }
01719 
01720 static void send_link_dtmf(struct rpt *myrpt,char c)
01721 {
01722 char  str[300];
01723 struct   ast_frame wf;
01724 struct   rpt_link *l;
01725 
01726    snprintf(str, sizeof(str), "D %s %s %d %c", myrpt->cmdnode, myrpt->name, ++(myrpt->dtmfidx), c);
01727    wf.frametype = AST_FRAME_TEXT;
01728    wf.subclass = 0;
01729    wf.offset = 0;
01730    wf.mallocd = 1;
01731    wf.datalen = strlen(str) + 1;
01732    wf.samples = 0;
01733    l = myrpt->links.next;
01734    /* first, see if our dude is there */
01735    while(l != &myrpt->links)
01736    {
01737       if (l->name[0] == '0') 
01738       {
01739          l = l->next;
01740          continue;
01741       }
01742       /* if we found it, write it and were done */
01743       if (!strcmp(l->name,myrpt->cmdnode))
01744       {
01745          wf.data = strdup(str);
01746          if (l->chan) ast_write(l->chan,&wf);
01747          return;
01748       }
01749       l = l->next;
01750    }
01751    l = myrpt->links.next;
01752    /* if not, give it to everyone */
01753    while(l != &myrpt->links)
01754    {
01755       wf.data = strdup(str);
01756       if (l->chan) ast_write(l->chan,&wf);
01757       l = l->next;
01758    }
01759    return;
01760 }
01761 
01762 /*
01763 * Internet linking function 
01764 */
01765 
01766 static int function_ilink(struct rpt *myrpt, char *param, char *digits, int command_source, struct rpt_link *mylink)
01767 {
01768 
01769    char *val, *s, *s1, *s2, *tele;
01770    char tmp[300], deststr[300] = "",modechange = 0;
01771    char digitbuf[MAXNODESTR];
01772    struct rpt_link *l;
01773    ZT_CONFINFO ci;  /* conference info */
01774 
01775    if(!param)
01776       return DC_ERROR;
01777       
01778          
01779    if (!myrpt->enable)
01780       return DC_ERROR;
01781 
01782    strncpy(digitbuf,digits,MAXNODESTR - 1);
01783 
01784    if(debug)
01785       printf("@@@@ ilink param = %s, digitbuf = %s\n", (param)? param : "(null)", digitbuf);
01786       
01787    switch(myatoi(param)){
01788       case 1: /* Link off */
01789          if ((digitbuf[0] == '0') && (myrpt->lastlinknode[0]))
01790             strcpy(digitbuf,myrpt->lastlinknode);
01791          val = ast_variable_retrieve(cfg, myrpt->nodes, digitbuf);
01792          if (!val){
01793             if(strlen(digitbuf) >= myrpt->longestnode)
01794                return DC_ERROR;
01795             break;
01796          }
01797          strncpy(tmp,val,sizeof(tmp) - 1);
01798          s = tmp;
01799          s1 = strsep(&s,",");
01800          s2 = strsep(&s,",");
01801          ast_mutex_lock(&myrpt->lock);
01802          l = myrpt->links.next;
01803          /* try to find this one in queue */
01804          while(l != &myrpt->links){
01805             if (l->name[0] == '0') 
01806             {
01807                l = l->next;
01808                continue;
01809             }
01810             /* if found matching string */
01811             if (!strcmp(l->name, digitbuf))
01812                break;
01813             l = l->next;
01814          }
01815          if (l != &myrpt->links){ /* if found */
01816             struct   ast_frame wf;
01817 
01818             strncpy(myrpt->lastlinknode,digitbuf,MAXNODESTR - 1);
01819             l->retries = MAX_RETRIES + 1;
01820             l->disced = 1;
01821             ast_mutex_unlock(&myrpt->lock);
01822             wf.frametype = AST_FRAME_TEXT;
01823             wf.subclass = 0;
01824             wf.offset = 0;
01825             wf.mallocd = 1;
01826             wf.datalen = strlen(discstr) + 1;
01827             wf.samples = 0;
01828             wf.data = strdup(discstr);
01829             if (l->chan)
01830             {
01831                ast_write(l->chan,&wf);
01832                if (ast_safe_sleep(l->chan,250) == -1) return DC_ERROR;
01833                ast_softhangup(l->chan,AST_SOFTHANGUP_DEV);
01834             }
01835             rpt_telemetry(myrpt, COMPLETE, NULL);
01836             return DC_COMPLETE;
01837          }
01838          ast_mutex_unlock(&myrpt->lock);  
01839          return DC_COMPLETE;
01840       case 2: /* Link Monitor */
01841          if ((digitbuf[0] == '0') && (myrpt->lastlinknode[0]))
01842             strcpy(digitbuf,myrpt->lastlinknode);
01843          val = ast_variable_retrieve(cfg, myrpt->nodes, digitbuf);
01844          if (!val){
01845             if(strlen(digitbuf) >= myrpt->longestnode)
01846                return DC_ERROR;
01847             break;
01848          }
01849          strncpy(tmp,val,sizeof(tmp) - 1);
01850          s = tmp;
01851          s1 = strsep(&s,",");
01852          s2 = strsep(&s,",");
01853          ast_mutex_lock(&myrpt->lock);
01854          l = myrpt->links.next;
01855          /* try to find this one in queue */
01856          while(l != &myrpt->links){
01857             if (l->name[0] == '0') 
01858             {
01859                l = l->next;
01860                continue;
01861             }
01862             /* if found matching string */
01863             if (!strcmp(l->name, digitbuf))
01864                break;
01865             l = l->next;
01866          }
01867          /* if found */
01868          if (l != &myrpt->links) 
01869          {
01870             /* if already in this mode, just ignore */
01871             if ((!l->mode) || (!l->chan)) {
01872                ast_mutex_unlock(&myrpt->lock);
01873                rpt_telemetry(myrpt,REMALREADY,NULL);
01874                return DC_COMPLETE;
01875                
01876             }
01877             ast_mutex_unlock(&myrpt->lock);
01878             if (l->chan) ast_softhangup(l->chan,AST_SOFTHANGUP_DEV);
01879             l->retries = MAX_RETRIES + 1;
01880             l->disced = 2;
01881             modechange = 1;
01882          } else
01883             ast_mutex_unlock(&myrpt->lock);
01884          strncpy(myrpt->lastlinknode,digitbuf,MAXNODESTR - 1);
01885          /* establish call in monitor mode */
01886          l = malloc(sizeof(struct rpt_link));
01887          if (!l){
01888             ast_log(LOG_WARNING, "Unable to malloc\n");
01889             return DC_ERROR;
01890          }
01891          /* zero the silly thing */
01892          memset((char *)l,0,sizeof(struct rpt_link));
01893          snprintf(deststr, sizeof(deststr), "IAX2/%s", s1);
01894          tele = strchr(deststr,'/');
01895          if (!tele){
01896             fprintf(stderr,"link2:Dial number (%s) must be in format tech/number\n",deststr);
01897             return DC_ERROR;
01898          }
01899          *tele++ = 0;
01900          l->isremote = (s && ast_true(s));
01901          strncpy(l->name, digitbuf, MAXNODESTR - 1);
01902          l->chan = ast_request(deststr,AST_FORMAT_SLINEAR,tele,NULL);
01903          if (modechange) l->connected = 1;
01904          if (l->chan){
01905             ast_set_read_format(l->chan,AST_FORMAT_SLINEAR);
01906             ast_set_write_format(l->chan,AST_FORMAT_SLINEAR);
01907             l->chan->whentohangup = 0;
01908             l->chan->appl = "Apprpt";
01909             l->chan->data = "(Remote Rx)";
01910             if (option_verbose > 2)
01911                ast_verbose(VERBOSE_PREFIX_3 "rpt (remote) initiating call to %s/%s on %s\n",
01912                   deststr,tele,l->chan->name);
01913             if(l->chan->cid.cid_num)
01914                free(l->chan->cid.cid_num);
01915             l->chan->cid.cid_num = strdup(myrpt->name);
01916             ast_call(l->chan,tele,0);
01917          }
01918          else
01919          {
01920             rpt_telemetry(myrpt,CONNFAIL,l);
01921             free(l);
01922             if (option_verbose > 2)
01923                ast_verbose(VERBOSE_PREFIX_3 "Unable to place call to %s/%s on %s\n",
01924                   deststr,tele,l->chan->name);
01925             return DC_ERROR;
01926          }
01927          /* allocate a pseudo-channel thru asterisk */
01928          l->pchan = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
01929          if (!l->pchan){
01930             fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
01931             ast_hangup(l->chan);
01932             free(l);
01933             return DC_ERROR;
01934          }
01935          ast_set_read_format(l->pchan,AST_FORMAT_SLINEAR);
01936          ast_set_write_format(l->pchan,AST_FORMAT_SLINEAR);
01937          /* make a conference for the pseudo-one */
01938          ci.chan = 0;
01939          ci.confno = myrpt->conf;
01940          ci.confmode = ZT_CONF_CONF | ZT_CONF_LISTENER | ZT_CONF_TALKER;
01941          /* first put the channel on the conference in proper mode */
01942          if (ioctl(l->pchan->fds[0],ZT_SETCONF,&ci) == -1)
01943          {
01944             ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
01945             ast_hangup(l->chan);
01946             ast_hangup(l->pchan);
01947             free(l);
01948             return DC_ERROR;
01949          }
01950          ast_mutex_lock(&myrpt->lock);
01951          /* insert at end of queue */
01952          insque((struct qelem *)l,(struct qelem *)myrpt->links.next);
01953          ast_mutex_unlock(&myrpt->lock);
01954          rpt_telemetry(myrpt,COMPLETE,NULL);
01955          return DC_COMPLETE;
01956       case 3: /* Link transceive */
01957          if ((digitbuf[0] == '0') && (myrpt->lastlinknode[0]))
01958             strcpy(digitbuf,myrpt->lastlinknode);
01959          val = ast_variable_retrieve(cfg, myrpt->nodes, digitbuf);
01960          if (!val){
01961             if(strlen(digitbuf) >= myrpt->longestnode)
01962                return DC_ERROR;
01963             break;
01964          }
01965          strncpy(tmp,val,sizeof(tmp) - 1);
01966          s = tmp;
01967          s1 = strsep(&s,",");
01968          s2 = strsep(&s,",");
01969          ast_mutex_lock(&myrpt->lock);
01970          l = myrpt->links.next;
01971          /* try to find this one in queue */
01972          while(l != &myrpt->links){
01973             if (l->name[0] == '0') 
01974             {
01975                l = l->next;
01976                continue;
01977             }
01978             /* if found matching string */
01979             if (!strcmp(l->name, digitbuf))
01980                break;
01981             l = l->next;
01982          }
01983          /* if found */
01984          if (l != &myrpt->links){ 
01985             /* if already in this mode, just ignore */
01986             if ((l->mode) || (!l->chan)) {
01987                ast_mutex_unlock(&myrpt->lock);
01988                rpt_telemetry(myrpt, REMALREADY, NULL);
01989                return DC_COMPLETE;
01990             }
01991             ast_mutex_unlock(&myrpt->lock);
01992             if (l->chan) ast_softhangup(l->chan, AST_SOFTHANGUP_DEV);
01993             l->retries = MAX_RETRIES + 1;
01994             l->disced = 2;
01995             modechange = 1;
01996          } else
01997             ast_mutex_unlock(&myrpt->lock);
01998          strncpy(myrpt->lastlinknode,digitbuf,MAXNODESTR - 1);
01999          /* establish call in tranceive mode */
02000          l = malloc(sizeof(struct rpt_link));
02001          if (!l){
02002             ast_log(LOG_WARNING, "Unable to malloc\n");
02003             return(DC_ERROR);
02004          }
02005          /* zero the silly thing */
02006          memset((char *)l,0,sizeof(struct rpt_link));
02007          l->mode = 1;
02008          l->outbound = 1;
02009          strncpy(l->name, digitbuf, MAXNODESTR - 1);
02010          l->isremote = (s && ast_true(s));
02011          if (modechange) l->connected = 1;
02012          snprintf(deststr, sizeof(deststr), "IAX2/%s", s1);
02013          tele = strchr(deststr, '/');
02014          if (!tele){
02015             fprintf(stderr,"link3:Dial number (%s) must be in format tech/number\n",deststr);
02016             free(l);
02017             return DC_ERROR;
02018          }
02019          *tele++ = 0;
02020          l->chan = ast_request(deststr, AST_FORMAT_SLINEAR, tele,NULL);
02021          if (l->chan){
02022             ast_set_read_format(l->chan, AST_FORMAT_SLINEAR);
02023             ast_set_write_format(l->chan, AST_FORMAT_SLINEAR);
02024             l->chan->whentohangup = 0;
02025             l->chan->appl = "Apprpt";
02026             l->chan->data = "(Remote Rx)";
02027             if (option_verbose > 2)
02028                ast_verbose(VERBOSE_PREFIX_3 "rpt (remote) initiating call to %s/%s on %s\n",
02029                   deststr, tele, l->chan->name);
02030             if(l->chan->cid.cid_num)
02031                free(l->chan->cid.cid_num);
02032             l->chan->cid.cid_num = strdup(myrpt->name);
02033             ast_call(l->chan,tele,999);
02034          }
02035          else{
02036             rpt_telemetry(myrpt,CONNFAIL,l);
02037             free(l);
02038             if (option_verbose > 2)
02039                ast_verbose(VERBOSE_PREFIX_3 "Unable to place call to %s/%s on %s\n",
02040                   deststr,tele,l->chan->name);
02041             return DC_ERROR;
02042          }
02043          /* allocate a pseudo-channel thru asterisk */
02044          l->pchan = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
02045          if (!l->pchan){
02046             fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
02047             ast_hangup(l->chan);
02048             free(l);
02049             return DC_ERROR;
02050          }
02051          ast_set_read_format(l->pchan, AST_FORMAT_SLINEAR);
02052          ast_set_write_format(l->pchan, AST_FORMAT_SLINEAR);
02053          /* make a conference for the tx */
02054          ci.chan = 0;
02055          ci.confno = myrpt->conf;
02056          ci.confmode = ZT_CONF_CONF | ZT_CONF_LISTENER | ZT_CONF_TALKER;
02057          /* first put the channel on the conference in proper mode */
02058          if (ioctl(l->pchan->fds[0], ZT_SETCONF, &ci) == -1)
02059          {
02060             ast_log(LOG_WARNING, "Unable to set conference mode to Announce\n");
02061             ast_hangup(l->chan);
02062             ast_hangup(l->pchan);
02063             free(l);
02064             return DC_ERROR;
02065          }
02066          ast_mutex_lock(&myrpt->lock);
02067          /* insert at end of queue */
02068          insque((struct qelem *)l,(struct qelem *)myrpt->links.next);
02069          ast_mutex_unlock(&myrpt->lock);
02070          rpt_telemetry(myrpt,COMPLETE,NULL);
02071          return DC_COMPLETE;
02072       case 4: /* Enter Command Mode */
02073       
02074          /* if doesnt allow link cmd, or no links active, return */
02075          if (((command_source != SOURCE_RPT) && (command_source != SOURCE_PHONE) && (command_source != SOURCE_DPHONE)) || (myrpt->links.next == &myrpt->links))
02076             return DC_COMPLETE;
02077          
02078          /* if already in cmd mode, or selected self, fughetabahtit */
02079          if ((myrpt->cmdnode[0]) || (!strcmp(myrpt->name, digitbuf))){
02080          
02081             rpt_telemetry(myrpt, REMALREADY, NULL);
02082             return DC_COMPLETE;
02083          }
02084          if ((digitbuf[0] == '0') && (myrpt->lastlinknode[0]))
02085             strcpy(digitbuf,myrpt->lastlinknode);
02086          /* node must at least exist in list */
02087          val = ast_variable_retrieve(cfg, myrpt->nodes, digitbuf);
02088          if (!val){
02089             if(strlen(digitbuf) >= myrpt->longestnode)
02090                return DC_ERROR;
02091             break;
02092          
02093          }
02094          ast_mutex_lock(&myrpt->lock);
02095          strcpy(myrpt->lastlinknode,digitbuf);
02096          strncpy(myrpt->cmdnode, digitbuf, sizeof(myrpt->cmdnode) - 1);
02097          ast_mutex_unlock(&myrpt->lock);
02098          rpt_telemetry(myrpt, REMGO, NULL);  
02099          return DC_COMPLETE;
02100          
02101       case 5: /* Status */
02102          rpt_telemetry(myrpt, STATUS, NULL);
02103          return DC_COMPLETE;
02104          
02105          
02106       case 6: /* All Links Off */
02107          l = myrpt->links.next;
02108          
02109          while(l != &myrpt->links){
02110             if (l->chan) ast_softhangup(l->chan, AST_SOFTHANGUP_DEV); /* Hang 'em up */
02111             l = l->next;
02112          }
02113          rpt_telemetry(myrpt, COMPLETE, NULL);
02114          break;
02115    
02116       default:
02117          return DC_ERROR;
02118          
02119    }
02120    
02121    return DC_INDETERMINATE;
02122 }  
02123 
02124 /*
02125 * Autopatch up
02126 */
02127 
02128 static int function_autopatchup(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink)
02129 {
02130    pthread_attr_t attr;
02131    
02132       
02133    if (!myrpt->enable)
02134       return DC_ERROR;
02135       
02136    if(debug)
02137       printf("@@@@ Autopatch up\n");
02138 
02139    ast_mutex_lock(&myrpt->lock);
02140    
02141    /* if on call, force * into current audio stream */
02142    
02143    if ((myrpt->callmode == 2) || (myrpt->callmode == 3)){
02144       myrpt->mydtmf = myrpt->funcchar;
02145    }
02146    if (myrpt->callmode){
02147       ast_mutex_unlock(&myrpt->lock);
02148       return DC_COMPLETE;
02149    }
02150    myrpt->callmode = 1;
02151    myrpt->cidx = 0;
02152    myrpt->exten[myrpt->cidx] = 0;
02153    ast_mutex_unlock(&myrpt->lock);
02154    pthread_attr_init(&attr);
02155    pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
02156    ast_pthread_create(&myrpt->rpt_call_thread,&attr,rpt_call,(void *) myrpt);
02157    return DC_COMPLETE;
02158 }
02159 
02160 /*
02161 * Autopatch down
02162 */
02163 
02164 static int function_autopatchdn(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink)
02165 {
02166    if (!myrpt->enable)
02167       return DC_ERROR;
02168    
02169    if(debug)
02170       printf("@@@@ Autopatch down\n");
02171       
02172    ast_mutex_lock(&myrpt->lock);
02173    
02174    if (!myrpt->callmode){
02175       ast_mutex_unlock(&myrpt->lock);
02176       return DC_COMPLETE;
02177    }
02178    
02179    myrpt->callmode = 0;
02180    ast_mutex_unlock(&myrpt->lock);
02181    rpt_telemetry(myrpt, TERM, NULL);
02182    return DC_COMPLETE;
02183 }
02184 
02185 /*
02186 * Status
02187 */
02188 
02189 static int function_status(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink)
02190 {
02191 
02192    if(!param)
02193       return DC_ERROR;
02194       
02195          
02196    if (!myrpt->enable)
02197       return DC_ERROR;
02198 
02199    if(debug)
02200       printf("@@@@ status param = %s, digitbuf = %s\n", (param)? param : "(null)", digitbuf);
02201    
02202    switch(myatoi(param)){
02203       case 1: /* System ID */
02204          rpt_telemetry(myrpt, ID1, NULL);
02205          return DC_COMPLETE;
02206       case 2: /* System Time */
02207          rpt_telemetry(myrpt, STATS_TIME, NULL);
02208          return DC_COMPLETE;
02209       case 3: /* app_rpt.c version */
02210          rpt_telemetry(myrpt, STATS_VERSION, NULL);
02211       default:
02212          return DC_ERROR;
02213    }
02214    return DC_INDETERMINATE;
02215 }
02216 
02217 /*
02218 * COP - Control operator
02219 */
02220 
02221 static int function_cop(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink)
02222 {
02223    if(!param)
02224       return DC_ERROR;
02225    
02226    switch(myatoi(param)){
02227       case 1: /* System reset */
02228          system("killall -9 asterisk"); /* FIXME to drastic? */
02229          return DC_COMPLETE;
02230 
02231       case 2:
02232          myrpt->enable = 1;
02233          rpt_telemetry(myrpt, ARB_ALPHA, (void *) "RPTENA");
02234          return DC_COMPLETE;
02235          
02236       case 3:
02237          myrpt->enable = 0;
02238          return DC_COMPLETE;
02239          
02240       case 4: /* test tone on */
02241          rpt_telemetry(myrpt, TEST_TONE, NULL);
02242          return DC_COMPLETE;
02243 
02244       case 5: /* Disgorge variables to log for debug purposes */
02245          myrpt->disgorgetime = time(NULL) + 10; /* Do it 10 seconds later */
02246          return DC_COMPLETE;
02247 
02248       case 6: /* Simulate COR being activated (phone only) */
02249          if (command_source != SOURCE_PHONE) return DC_INDETERMINATE;
02250          return DC_DOKEY;  
02251 
02252    }  
02253    return DC_INDETERMINATE;
02254 }
02255 
02256 /*
02257 * Collect digits one by one until something matches
02258 */
02259 
02260 static int collect_function_digits(struct rpt *myrpt, char *digits, 
02261    int command_source, struct rpt_link *mylink)
02262 {
02263    int i;
02264    char *stringp,*action,*param,*functiondigits;
02265    char function_table_name[30] = "";
02266    char workstring[80];
02267    
02268    struct ast_variable *vp;
02269    
02270    if(debug)   
02271       printf("@@@@ Digits collected: %s, source: %d\n", digits, command_source);
02272    
02273    if (command_source == SOURCE_DPHONE) {
02274       if (!myrpt->dphone_functions) return DC_INDETERMINATE;
02275       strncpy(function_table_name, myrpt->dphone_functions, sizeof(function_table_name) - 1);
02276       }
02277    else if (command_source == SOURCE_PHONE) {
02278       if (!myrpt->phone_functions) return DC_INDETERMINATE;
02279       strncpy(function_table_name, myrpt->phone_functions, sizeof(function_table_name) - 1);
02280       }
02281    else if (command_source == SOURCE_LNK)
02282       strncpy(function_table_name, myrpt->link_functions, sizeof(function_table_name) - 1);
02283    else
02284       strncpy(function_table_name, myrpt->functions, sizeof(function_table_name) - 1);
02285    vp = ast_variable_browse(cfg, function_table_name);
02286    while(vp) {
02287       if(!strncasecmp(vp->name, digits, strlen(vp->name)))
02288          break;
02289       vp = vp->next;
02290    }  
02291    if(!vp) {
02292       int n;
02293 
02294       n = myrpt->longestfunc;
02295       if (command_source == SOURCE_LNK) n = myrpt->link_longestfunc;
02296       else 
02297       if (command_source == SOURCE_PHONE) n = myrpt->phone_longestfunc;
02298       else 
02299       if (command_source == SOURCE_DPHONE) n = myrpt->dphone_longestfunc;
02300       
02301       if(strlen(digits) >= n)
02302          return DC_ERROR;
02303       else
02304          return DC_INDETERMINATE;
02305    }  
02306    /* Found a match, retrieve value part and parse */
02307    strncpy(workstring, vp->value, sizeof(workstring) - 1 );
02308    stringp = workstring;
02309    action = strsep(&stringp, ",");
02310    param = stringp;
02311    if(debug)
02312       printf("@@@@ action: %s, param = %s\n",action, (param) ? param : "(null)");
02313    /* Look up the action */
02314    for(i = 0 ; i < (sizeof(function_table)/sizeof(struct function_table_tag)); i++){
02315       if(!strncasecmp(action, function_table[i].action, strlen(action)))
02316          break;
02317    }
02318    if(debug)
02319       printf("@@@@ table index i = %d\n",i);
02320    if(i == (sizeof(function_table)/sizeof(struct function_table_tag))){
02321       /* Error, action not in table */
02322       return DC_ERROR;
02323    }
02324    if(function_table[i].function == NULL){
02325       /* Error, function undefined */
02326       if(debug)
02327          printf("@@@@ NULL for action: %s\n",action);
02328       return DC_ERROR;
02329    }
02330    functiondigits = digits + strlen(vp->name);
02331    return (*function_table[i].function)(myrpt, param, functiondigits, command_source, mylink);
02332 }
02333 
02334 
02335 static void handle_link_data(struct rpt *myrpt, struct rpt_link *mylink,
02336    char *str)
02337 {
02338 char  tmp[300],cmd[300] = "",dest[300],src[300],c;
02339 int   seq, res;
02340 struct rpt_link *l;
02341 struct   ast_frame wf;
02342 
02343    wf.frametype = AST_FRAME_TEXT;
02344    wf.subclass = 0;
02345    wf.offset = 0;
02346    wf.mallocd = 1;
02347    wf.datalen = strlen(str) + 1;
02348    wf.samples = 0;
02349    /* put string in our buffer */
02350    strncpy(tmp,str,sizeof(tmp) - 1);
02351 
02352         if (!strcmp(tmp,discstr))
02353         {
02354                 mylink->disced = 1;
02355       mylink->retries = MAX_RETRIES + 1;
02356                 ast_softhangup(mylink->chan,AST_SOFTHANGUP_DEV);
02357                 return;
02358         }
02359    if (sscanf(tmp,"%s %s %s %d %c",cmd,dest,src,&seq,&c) != 5)
02360    {
02361       ast_log(LOG_WARNING, "Unable to parse link string %s\n",str);
02362       return;
02363    }
02364    if (strcmp(cmd,"D"))
02365    {
02366       ast_log(LOG_WARNING, "Unable to parse link string %s\n",str);
02367       return;
02368    }
02369 
02370    if (dest[0] == '0')
02371    {
02372       strcpy(dest,myrpt->name);
02373    }     
02374 
02375    /* if not for me, redistribute to all links */
02376    if (strcmp(dest,myrpt->name))
02377    {
02378       l = myrpt->links.next;
02379       /* see if this is one in list */
02380       while(l != &myrpt->links)
02381       {
02382          if (l->name[0] == '0') 
02383          {
02384             l = l->next;
02385             continue;
02386          }
02387          /* dont send back from where it came */
02388          if ((l == mylink) || (!strcmp(l->name,mylink->name)))
02389          {
02390             l = l->next;
02391             continue;
02392          }
02393          /* if it is, send it and we're done */
02394          if (!strcmp(l->name,dest))
02395          {
02396             /* send, but not to src */
02397             if (strcmp(l->name,src)) {
02398                wf.data = strdup(str);
02399                if (l->chan) ast_write(l->chan,&wf);
02400             }
02401             return;
02402          }
02403          l = l->next;
02404       }
02405       l = myrpt->links.next;
02406       /* otherwise, send it to all of em */
02407       while(l != &myrpt->links)
02408       {
02409          if (l->name[0] == '0') 
02410          {
02411             l = l->next;
02412             continue;
02413          }
02414          /* dont send back from where it came */
02415          if ((l == mylink) || (!strcmp(l->name,mylink->name)))
02416          {
02417             l = l->next;
02418             continue;
02419          }
02420          /* send, but not to src */
02421          if (strcmp(l->name,src)) {
02422             wf.data = strdup(str);
02423             if (l->chan) ast_write(l->chan,&wf);
02424          }
02425          l = l->next;
02426       }
02427       return;
02428    }
02429    ast_mutex_lock(&myrpt->lock);
02430    if (c == myrpt->endchar) myrpt->stopgen = 1;
02431    if (myrpt->callmode == 1)
02432    {
02433       myrpt->exten[myrpt->cidx++] = c;
02434       myrpt->exten[myrpt->cidx] = 0;
02435       /* if this exists */
02436       if (ast_exists_extension(myrpt->pchannel,myrpt->ourcontext,myrpt->exten,1,NULL))
02437       {
02438          myrpt->callmode = 2;
02439          rpt_telemetry(myrpt,PROC,NULL); 
02440       }
02441       /* if can continue, do so */
02442       if (!ast_canmatch_extension(myrpt->pchannel,myrpt->ourcontext,myrpt->exten,1,NULL)) 
02443       {
02444          /* call has failed, inform user */
02445          myrpt->callmode = 4;
02446       }
02447    }
02448    if ((myrpt->callmode == 2) || (myrpt->callmode == 3))
02449    {
02450       myrpt->mydtmf = c;
02451    }
02452    if (c == myrpt->funcchar)
02453    {
02454       myrpt->rem_dtmfidx = 0;
02455       myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx] = 0;
02456       time(&myrpt->rem_dtmf_time);
02457       ast_mutex_unlock(&myrpt->lock);
02458       return;
02459    } 
02460    else if ((c != myrpt->endchar) && (myrpt->rem_dtmfidx >= 0))
02461    {
02462       time(&myrpt->rem_dtmf_time);
02463       if (myrpt->rem_dtmfidx < MAXDTMF)
02464       {
02465          myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx++] = c;
02466          myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx] = 0;
02467          
02468          ast_mutex_unlock(&myrpt->lock);
02469          strncpy(cmd, myrpt->rem_dtmfbuf, sizeof(cmd) - 1);
02470          res = collect_function_digits(myrpt, cmd, SOURCE_LNK, mylink);
02471          ast_mutex_lock(&myrpt->lock);
02472          
02473          switch(res){
02474 
02475             case DC_INDETERMINATE:
02476                break;
02477             
02478             case DC_REQ_FLUSH:
02479                myrpt->rem_dtmfidx = 0;
02480                myrpt->rem_dtmfbuf[0] = 0;
02481                break;
02482             
02483             
02484             case DC_COMPLETE:
02485                myrpt->rem_dtmfbuf[0] = 0;
02486                myrpt->rem_dtmfidx = -1;
02487                myrpt->rem_dtmf_time = 0;
02488                break;
02489             
02490             case DC_ERROR:
02491             default:
02492                myrpt->rem_dtmfbuf[0] = 0;
02493                myrpt->rem_dtmfidx = -1;
02494                myrpt->rem_dtmf_time = 0;
02495                break;
02496          }
02497       }
02498 
02499    }
02500    ast_mutex_unlock(&myrpt->lock);
02501    return;
02502 }
02503 
02504 static void handle_link_phone_dtmf(struct rpt *myrpt, struct rpt_link *mylink,
02505    char c)
02506 {
02507 
02508 char  cmd[300];
02509 int   res;
02510 
02511    ast_mutex_lock(&myrpt->lock);
02512    if (c == myrpt->endchar)
02513    {
02514       if (mylink->lastrx)
02515       {
02516          mylink->lastrx = 0;
02517          ast_mutex_unlock(&myrpt->lock);
02518          return;
02519       }
02520       myrpt->stopgen = 1;
02521       if (myrpt->cmdnode[0])
02522       {
02523          myrpt->cmdnode[0] = 0;
02524          myrpt->dtmfidx = -1;
02525          myrpt->dtmfbuf[0] = 0;
02526          ast_mutex_unlock(&myrpt->lock);
02527          rpt_telemetry(myrpt,COMPLETE,NULL);
02528          ast_mutex_unlock(&myrpt->lock);
02529          return;
02530       }
02531    }
02532    if (myrpt->cmdnode[0])
02533    {
02534       ast_mutex_unlock(&myrpt->lock);
02535       send_link_dtmf(myrpt,c);
02536       return;
02537    }
02538    if (myrpt->callmode == 1)
02539    {
02540       myrpt->exten[myrpt->cidx++] = c;
02541       myrpt->exten[myrpt->cidx] = 0;
02542       /* if this exists */
02543       if (ast_exists_extension(myrpt->pchannel,myrpt->ourcontext,myrpt->exten,1,NULL))
02544       {
02545          myrpt->callmode = 2;
02546          rpt_telemetry(myrpt,PROC,NULL); 
02547       }
02548       /* if can continue, do so */
02549       if (!ast_canmatch_extension(myrpt->pchannel,myrpt->ourcontext,myrpt->exten,1,NULL)) 
02550       {
02551          /* call has failed, inform user */
02552          myrpt->callmode = 4;
02553       }
02554    }
02555    if ((myrpt->callmode == 2) || (myrpt->callmode == 3))
02556    {
02557       myrpt->mydtmf = c;
02558    }
02559    if (c == myrpt->funcchar)
02560    {
02561       myrpt->rem_dtmfidx = 0;
02562       myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx] = 0;
02563       time(&myrpt->rem_dtmf_time);
02564       ast_mutex_unlock(&myrpt->lock);
02565       return;
02566    } 
02567    else if ((c != myrpt->endchar) && (myrpt->rem_dtmfidx >= 0))
02568    {
02569       time(&myrpt->rem_dtmf_time);
02570       if (myrpt->rem_dtmfidx < MAXDTMF)
02571       {
02572          myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx++] = c;
02573          myrpt->rem_dtmfbuf[myrpt->rem_dtmfidx] = 0;
02574          
02575          ast_mutex_unlock(&myrpt->lock);
02576          strncpy(cmd, myrpt->rem_dtmfbuf, sizeof(cmd) - 1);
02577          res = collect_function_digits(myrpt, cmd, 
02578             ((mylink->phonemode == 2) ? SOURCE_DPHONE : SOURCE_PHONE), mylink);
02579          ast_mutex_lock(&myrpt->lock);
02580          
02581          switch(res){
02582 
02583             case DC_INDETERMINATE:
02584                break;
02585             
02586             case DC_DOKEY:
02587                mylink->lastrx = 1;
02588                break;
02589             
02590             case DC_REQ_FLUSH:
02591                myrpt->rem_dtmfidx = 0;
02592                myrpt->rem_dtmfbuf[0] = 0;
02593                break;
02594             
02595             
02596             case DC_COMPLETE:
02597                myrpt->rem_dtmfbuf[0] = 0;
02598                myrpt->rem_dtmfidx = -1;
02599                myrpt->rem_dtmf_time = 0;
02600                break;
02601             
02602             case DC_ERROR:
02603             default:
02604                myrpt->rem_dtmfbuf[0] = 0;
02605                myrpt->rem_dtmfidx = -1;
02606                myrpt->rem_dtmf_time = 0;
02607                break;
02608          }
02609       }
02610 
02611    }
02612    ast_mutex_unlock(&myrpt->lock);
02613    return;
02614 }
02615 
02616 /* Doug Hall RBI-1 serial data definitions:
02617  *
02618  * Byte 0: Expansion external outputs 
02619  * Byte 1: 
02620  * Bits 0-3 are BAND as follows:
02621  * Bits 4-5 are POWER bits as follows:
02622  *    00 - Low Power
02623  *    01 - Hi Power
02624  *    02 - Med Power
02625  * Bits 6-7 are always set
02626  * Byte 2:
02627  * Bits 0-3 MHZ in BCD format
02628  * Bits 4-5 are offset as follows:
02629  *    00 - minus
02630  *    01 - plus
02631  *    02 - simplex
02632  *    03 - minus minus (whatever that is)
02633  * Bit 6 is the 0/5 KHZ bit
02634  * Bit 7 is always set
02635  * Byte 3:
02636  * Bits 0-3 are 10 KHZ in BCD format
02637  * Bits 4-7 are 100 KHZ in BCD format
02638  * Byte 4: PL Tone code and encode/decode enable bits
02639  * Bits 0-5 are PL tone code (comspec binary codes)
02640  * Bit 6 is encode enable/disable
02641  * Bit 7 is decode enable/disable
02642  */
02643 
02644 /* take the frequency from the 10 mhz digits (and up) and convert it
02645    to a band number */
02646 
02647 static int rbi_mhztoband(char *str)
02648 {
02649 int   i;
02650 
02651    i = atoi(str) / 10; /* get the 10's of mhz */
02652    switch(i)
02653    {
02654        case 2:
02655       return 10;
02656        case 5:
02657       return 11;
02658        case 14:
02659       return 2;
02660        case 22:
02661       return 3;
02662        case 44:
02663       return 4;
02664        case 124:
02665       return 0;
02666        case 125:
02667       return 1;
02668        case 126:
02669       return 8;
02670        case 127:
02671       return 5;
02672        case 128:
02673       return 6;
02674        case 129:
02675       return 7;
02676        default:
02677       break;
02678    }
02679    return -1;
02680 }
02681 
02682 /* take a PL frequency and turn it into a code */
02683 static int rbi_pltocode(char *str)
02684 {
02685 int i;
02686 char *s;
02687 
02688    s = strchr(str,'.');
02689    i = 0;
02690    if (s) i = atoi(s + 1);
02691    i += atoi(str) * 10;
02692    switch(i)
02693    {
02694        case 670:
02695       return 0;
02696        case 719:
02697       return 1;
02698        case 744:
02699       return 2;
02700        case 770:
02701       return 3;
02702        case 797:
02703       return 4;
02704        case 825:
02705       return 5;
02706        case 854:
02707       return 6;
02708        case 885:
02709       return 7;
02710        case 915:
02711       return 8;
02712        case 948:
02713       return 9;
02714        case 974:
02715       return 10;
02716        case 1000:
02717       return 11;
02718        case 1035:
02719       return 12;
02720        case 1072:
02721       return 13;
02722        case 1109:
02723       return 14;
02724        case 1148:
02725       return 15;
02726        case 1188:
02727       return 16;
02728        case 1230:
02729       return 17;
02730        case 1273:
02731       return 18;
02732        case 1318:
02733       return 19;
02734        case 1365:
02735       return 20;
02736        case 1413:
02737       return 21;
02738        case 1462:
02739       return 22;
02740        case 1514:
02741       return 23;
02742        case 1567:
02743       return 24;
02744        case 1622:
02745       return 25;
02746        case 1679:
02747       return 26;
02748        case 1738:
02749       return 27;
02750        case 1799:
02751       return 28;
02752        case 1862:
02753       return 29;
02754        case 1928:
02755       return 30;
02756        case 2035:
02757       return 31;
02758        case 2107:
02759       return 32;
02760        case 2181:
02761       return 33;
02762        case 2257:
02763       return 34;
02764        case 2336:
02765       return 35;
02766        case 2418:
02767       return 36;
02768        case 2503:
02769       return 37;
02770    }
02771    return -1;
02772 }
02773 
02774 /*
02775 * Shift out a formatted serial bit stream
02776 */
02777 
02778 static void rbi_out_parallel(struct rpt *myrpt,unsigned char *data)
02779     {
02780     int i,j;
02781     unsigned char od,d;
02782     static volatile long long delayvar;
02783 
02784     for(i = 0 ; i < 5 ; i++){
02785         od = *data++; 
02786         for(j = 0 ; j < 8 ; j++){
02787             d = od & 1;
02788             outb(d,myrpt->iobase);
02789        /* >= 15 us */
02790        for(delayvar = 1; delayvar < 15000; delayvar++); 
02791             od >>= 1;
02792             outb(d | 2,myrpt->iobase);
02793        /* >= 30 us */
02794        for(delayvar = 1; delayvar < 30000; delayvar++); 
02795             outb(d,myrpt->iobase);
02796        /* >= 10 us */
02797        for(delayvar = 1; delayvar < 10000; delayvar++); 
02798             }
02799         }
02800    /* >= 50 us */
02801         for(delayvar = 1; delayvar < 50000; delayvar++); 
02802     }
02803 
02804 static void rbi_out(struct rpt *myrpt,unsigned char *data)
02805 {
02806 struct zt_radio_param r;
02807 
02808    memset(&r,0,sizeof(struct zt_radio_param));
02809    r.radpar = ZT_RADPAR_REMMODE;
02810    r.data = ZT_RADPAR_REM_RBI1;
02811    /* if setparam ioctl fails, its probably not a pciradio card */
02812    if (ioctl(myrpt->rxchannel->fds[0],ZT_RADIO_SETPARAM,&r) == -1)
02813    {
02814       rbi_out_parallel(myrpt,data);
02815       return;
02816    }
02817    r.radpar = ZT_RADPAR_REMCOMMAND;
02818    memcpy(&r.data,data,5);
02819    if (ioctl(myrpt->rxchannel->fds[0],ZT_RADIO_SETPARAM,&r) == -1)
02820    {
02821       ast_log(LOG_WARNING,"Cannot send RBI command for channel %s\n",myrpt->rxchannel->name);
02822       return;
02823    }
02824 }
02825 
02826 static int serial_remote_io(struct rpt *myrpt, char *txbuf, int txbytes, char *rxbuf,
02827         int rxmaxbytes, int asciiflag)
02828 {
02829    int i;
02830    struct zt_radio_param prm;
02831 
02832    if(debug){
02833       printf("String output was: ");
02834       for(i = 0; i < txbytes; i++)
02835          printf("%02X ", (unsigned char ) txbuf[i]);
02836       printf("\n");
02837    }
02838 
02839         prm.radpar = ZT_RADPAR_REMMODE;
02840         if (asciiflag)  prm.data = ZT_RADPAR_REM_SERIAL_ASCII;
02841         else prm.data = ZT_RADPAR_REM_SERIAL;
02842    if (ioctl(myrpt->rxchannel->fds[0],ZT_RADIO_SETPARAM,&prm) == -1) return -1;
02843         prm.radpar = ZT_RADPAR_REMCOMMAND;
02844         prm.data = rxmaxbytes;
02845         memcpy(prm.buf,txbuf,txbytes);
02846         prm.index = txbytes;
02847    if (ioctl(myrpt->rxchannel->fds[0],ZT_RADIO_SETPARAM,&prm) == -1) return -1;
02848         if (rxbuf)
02849         {
02850                 *rxbuf = 0;
02851                 memcpy(rxbuf,prm.buf,prm.index);
02852         }
02853         return(prm.index);
02854 }
02855 
02856 static int setrbi(struct rpt *myrpt)
02857 {
02858 char tmp[MAXREMSTR] = "",rbicmd[5],*s;
02859 int   band,txoffset = 0,txpower = 0,txpl;
02860 
02861    /* must be a remote system */
02862    if (!myrpt->remote) return(0);
02863    /* must have rbi hardware */
02864    if (strncmp(myrpt->remote,remote_rig_rbi,3)) return(0);
02865    strncpy(tmp, myrpt->freq, sizeof(tmp) - 1);
02866    s = strchr(tmp,'.');
02867    /* if no decimal, is invalid */
02868    
02869    if (s == NULL){
02870       if(debug)
02871          printf("@@@@ Frequency needs a decimal\n");
02872       return -1;
02873    }
02874    
02875    *s++ = 0;
02876    if (strlen(tmp) < 2){
02877       if(debug)
02878          printf("@@@@ Bad MHz digits: %s\n", tmp);
02879       return -1;
02880    }
02881     
02882    if (strlen(s) < 3){
02883       if(debug)
02884          printf("@@@@ Bad KHz digits: %s\n", s);
02885       return -1;
02886    }
02887 
02888    if ((s[2] != '0') && (s[2] != '5')){
02889       if(debug)
02890          printf("@@@@ KHz must end in 0 or 5: %c\n", s[2]);
02891       return -1;
02892    }
02893     
02894    band = rbi_mhztoband(tmp);
02895    if (band == -1){
02896       if(debug)
02897          printf("@@@@ Bad Band: %s\n", tmp);
02898       return -1;
02899    }
02900    
02901    txpl = rbi_pltocode(myrpt->txpl);
02902    
02903    if (txpl == -1){
02904       if(debug)
02905          printf("@@@@ Bad TX PL: %s\n", myrpt->txpl);
02906       return -1;
02907    }
02908 
02909    
02910    switch(myrpt->offset)
02911    {
02912        case REM_MINUS:
02913       txoffset = 0;
02914       break;
02915        case REM_PLUS:
02916       txoffset = 0x10;
02917       break;
02918        case REM_SIMPLEX:
02919       txoffset = 0x20;
02920       break;
02921    }
02922    switch(myrpt->powerlevel)
02923    {
02924        case REM_LOWPWR:
02925       txpower = 0;
02926       break;
02927        case REM_MEDPWR:
02928       txpower = 0x20;
02929       break;
02930        case REM_HIPWR:
02931       txpower = 0x10;
02932       break;
02933    }
02934    rbicmd[0] = 0;
02935    rbicmd[1] = band | txpower | 0xc0;
02936    rbicmd[2] = (*(s - 2) - '0') | txoffset | 0x80;
02937    if (s[2] == '5') rbicmd[2] |= 0x40;
02938    rbicmd[3] = ((*s - '0') << 4) + (s[1] - '0');
02939    rbicmd[4] = txpl;
02940    if (myrpt->txplon) rbicmd[4] |= 0x40;
02941    if (myrpt->rxplon) rbicmd[4] |= 0x80;
02942    rbi_out(myrpt,rbicmd);
02943    return 0;
02944 }
02945 
02946 
02947 /* Check for valid rbi frequency */
02948 /* Hard coded limits now, configurable later, maybe? */
02949 
02950 static int check_freq_rbi(int m, int d, int *defmode)
02951 {
02952    int dflmd = REM_MODE_FM;
02953 
02954    if(m == 50){ /* 6 meters */
02955       if(d < 10100)
02956          return -1;
02957    }
02958    else if((m >= 51) && ( m < 54)){
02959                 ;
02960    }
02961    else if(m == 144){ /* 2 meters */
02962       if(d < 10100)
02963          return -1;
02964    }
02965    else if((m >= 145) && (m < 148)){
02966       ;
02967    }
02968    else if((m >= 222) && (m < 225)){ /* 1.25 meters */
02969       ;
02970    }
02971    else if((m >= 430) && (m < 450)){ /* 70 centimeters */
02972       ;
02973    }
02974    else if((m >= 1240) && (m < 1300)){ /* 23 centimeters */
02975       ;
02976    }
02977    else
02978       return -1;
02979    
02980    if(defmode)
02981       *defmode = dflmd; 
02982 
02983 
02984    return 0;
02985 }
02986 
02987 /*
02988 * Split frequency into mhz and decimals
02989 */
02990  
02991 static int split_freq(char *mhz, char *decimals, char *freq)
02992 {
02993    char freq_copy[MAXREMSTR];
02994    char *decp;
02995 
02996    decp = strchr(strncpy(freq_copy, freq, MAXREMSTR),'.');
02997    if(decp){
02998       *decp++ = 0;
02999       strncpy(mhz, freq_copy, MAXREMSTR);
03000       strcpy(decimals, "00000");
03001       strncpy(decimals, decp, strlen(decp));
03002       decimals[5] = 0;
03003       return 0;
03004    }
03005    else
03006       return -1;
03007 
03008 }
03009    
03010 /*
03011 * Split ctcss frequency into hertz and decimal
03012 */
03013  
03014 static int split_ctcss_freq(char *hertz, char *decimal, char *freq)
03015 {
03016    char freq_copy[MAXREMSTR];
03017    char *decp;
03018 
03019    decp = strchr(strncpy(freq_copy, freq, MAXREMSTR),'.');
03020    if(decp){
03021       *decp++ = 0;
03022       strncpy(hertz, freq_copy, MAXREMSTR);
03023       strncpy(decimal, decp, strlen(decp));
03024       decimal[strlen(decp)] = '\0';
03025       return 0;
03026    }
03027    else
03028       return -1;
03029 }
03030 
03031 
03032 
03033 /*
03034 * FT-897 I/O handlers
03035 */
03036 
03037 /* Check to see that the frequency is valid */
03038 /* Hard coded limits now, configurable later, maybe? */
03039 
03040 
03041 static int check_freq_ft897(int m, int d, int *defmode)
03042 {
03043    int dflmd = REM_MODE_FM;
03044 
03045    if(m == 1){ /* 160 meters */
03046       dflmd =  REM_MODE_LSB; 
03047       if(d < 80001)
03048          return -1;
03049    }
03050    else if(m == 3){ /* 80 meters */
03051       dflmd = REM_MODE_LSB;
03052       if(d < 75001)
03053          return -1;
03054    }
03055    else if(m == 7){ /* 40 meters */
03056       dflmd = REM_MODE_LSB;
03057       if((d < 15001) || (d > 29999))
03058          return -1;
03059    }
03060    else if(m == 14){ /* 20 meters */
03061       dflmd = REM_MODE_USB;
03062       if((d < 15001) || (d > 34999))
03063          return -1;
03064    }
03065    else if(m == 18){ /* 17 meters */
03066       dflmd = REM_MODE_USB;
03067       if((d < 11001) || (d > 16797))
03068          return -1;
03069    }
03070    else if(m == 21){ /* 15 meters */
03071       dflmd = REM_MODE_USB;
03072       if((d < 20001) || (d > 44999))
03073          return -1;
03074    }
03075    else if(m == 24){ /* 12 meters */
03076       dflmd = REM_MODE_USB;
03077       if((d < 93001) || (d > 98999))
03078          return -1;
03079    }
03080    else if(m == 28){ /* 10 meters */
03081       dflmd = REM_MODE_USB;
03082       if(d < 30001)
03083          return -1;
03084    }
03085    else if(m == 29){ 
03086       if(d >= 51000)
03087          dflmd = REM_MODE_FM;
03088       else
03089          dflmd = REM_MODE_USB;
03090       if(d > 69999)
03091          return -1;
03092    }
03093    else if(m == 50){ /* 6 meters */
03094       if(d < 10100)
03095          return -1;
03096       if(d >= 30000)
03097          dflmd = REM_MODE_FM;
03098       else
03099          dflmd = REM_MODE_USB;
03100 
03101    }
03102    else if((m >= 51) && ( m < 54)){
03103       dflmd = REM_MODE_FM;
03104    }
03105    else if(m == 144){ /* 2 meters */
03106       if(d < 10100)
03107          return -1;
03108       if(d >= 30000)
03109          dflmd = REM_MODE_FM;
03110       else
03111          dflmd = REM_MODE_USB;
03112    }
03113    else if((m >= 145) && (m < 148)){
03114       dflmd = REM_MODE_FM;
03115    }
03116    else if((m >= 430) && (m < 450)){ /* 70 centimeters */
03117       if(m  < 438)
03118          dflmd = REM_MODE_USB;
03119       else
03120          dflmd = REM_MODE_FM;
03121       ;
03122    }
03123    else
03124       return -1;
03125 
03126    if(defmode)
03127       *defmode = dflmd;
03128 
03129    return 0;
03130 }
03131 
03132 /*
03133 * Set a new frequency for the FT897
03134 */
03135 
03136 static int set_freq_ft897(struct rpt *myrpt, char *newfreq)
03137 {
03138    char mhz[MAXREMSTR];
03139    char decimals[MAXREMSTR];
03140    unsigned char cmdstr[5];
03141    int fd,m,d;
03142 
03143    fd = 0;
03144    if(debug) 
03145       printf("New frequency: %s\n",newfreq);
03146 
03147    if(split_freq(mhz, decimals, newfreq))
03148       return -1; 
03149 
03150    m = atoi(mhz);
03151    d = atoi(decimals);
03152 
03153    /* The FT-897 likes packed BCD frequencies */
03154 
03155    cmdstr[0] = ((m / 100) << 4) + ((m % 100)/10);        /* 100MHz 10Mhz */
03156    cmdstr[1] = ((m % 10) << 4) + (d / 10000);         /* 1MHz 100KHz */
03157    cmdstr[2] = (((d % 10000)/1000) << 4) + ((d % 1000)/ 100);  /* 10KHz 1KHz */
03158    cmdstr[3] = (((d % 100)/10) << 4) + (d % 10);         /* 100Hz 10Hz */
03159    cmdstr[4] = 0x01;                /* command */
03160 
03161    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03162 
03163 }
03164 
03165 /* ft-897 simple commands */
03166 
03167 static int simple_command_ft897(struct rpt *myrpt, char command)
03168 {
03169    unsigned char cmdstr[5];
03170    
03171    memset(cmdstr, 0, 5);
03172 
03173    cmdstr[4] = command; 
03174 
03175    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03176 
03177 }
03178 
03179 /* ft-897 offset */
03180 
03181 static int set_offset_ft897(struct rpt *myrpt, char offset)
03182 {
03183    unsigned char cmdstr[5];
03184    
03185    memset(cmdstr, 0, 5);
03186 
03187    switch(offset){
03188       case  REM_SIMPLEX:
03189          cmdstr[0] = 0x89;
03190          break;
03191 
03192       case  REM_MINUS:
03193          cmdstr[0] = 0x09;
03194          break;
03195       
03196       case  REM_PLUS:
03197          cmdstr[0] = 0x49;
03198          break;   
03199 
03200       default:
03201          return -1;
03202    }
03203 
03204    cmdstr[4] = 0x09; 
03205 
03206    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03207 }
03208 
03209 /* ft-897 mode */
03210 
03211 static int set_mode_ft897(struct rpt *myrpt, char newmode)
03212 {
03213    unsigned char cmdstr[5];
03214    
03215    memset(cmdstr, 0, 5);
03216    
03217    switch(newmode){
03218       case  REM_MODE_FM:
03219          cmdstr[0] = 0x08;
03220          break;
03221 
03222       case  REM_MODE_USB:
03223          cmdstr[0] = 0x01;
03224          break;
03225 
03226       case  REM_MODE_LSB:
03227          cmdstr[0] = 0x00;
03228          break;
03229 
03230       case  REM_MODE_AM:
03231          cmdstr[0] = 0x04;
03232          break;
03233       
03234       default:
03235          return -1;
03236    }
03237    cmdstr[4] = 0x07; 
03238 
03239    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03240 }
03241 
03242 /* Set tone encode and decode modes */
03243 
03244 static int set_ctcss_mode_ft897(struct rpt *myrpt, char txplon, char rxplon)
03245 {
03246    unsigned char cmdstr[5];
03247    
03248    memset(cmdstr, 0, 5);
03249    
03250    if(rxplon && txplon)
03251       cmdstr[0] = 0x2A; /* Encode and Decode */
03252    else if (!rxplon && txplon)
03253       cmdstr[0] = 0x4A; /* Encode only */
03254    else if (rxplon && !txplon)
03255       cmdstr[0] = 0x3A; /* Encode only */
03256    else
03257       cmdstr[0] = 0x8A; /* OFF */
03258 
03259    cmdstr[4] = 0x0A; 
03260 
03261    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03262 }
03263 
03264 
03265 /* Set transmit and receive ctcss tone frequencies */
03266 
03267 static int set_ctcss_freq_ft897(struct rpt *myrpt, char *txtone, char *rxtone)
03268 {
03269    unsigned char cmdstr[5];
03270    char hertz[MAXREMSTR],decimal[MAXREMSTR];
03271    int h,d; 
03272 
03273    memset(cmdstr, 0, 5);
03274 
03275    if(split_ctcss_freq(hertz, decimal, txtone))
03276       return -1; 
03277 
03278    h = atoi(hertz);
03279    d = atoi(decimal);
03280    
03281    cmdstr[0] = ((h / 100) << 4) + (h % 100)/ 10;
03282    cmdstr[1] = ((h % 10) << 4) + (d % 10);
03283    
03284    if(rxtone){
03285    
03286       if(split_ctcss_freq(hertz, decimal, rxtone))
03287          return -1; 
03288 
03289       h = atoi(hertz);
03290       d = atoi(decimal);
03291    
03292       cmdstr[2] = ((h / 100) << 4) + (h % 100)/ 10;
03293       cmdstr[3] = ((h % 10) << 4) + (d % 10);
03294    }
03295    cmdstr[4] = 0x0B; 
03296 
03297    return serial_remote_io(myrpt, cmdstr, 5, NULL, 0, 0);
03298 }  
03299 
03300 
03301 
03302 static int set_ft897(struct rpt *myrpt)
03303 {
03304    int res;
03305    
03306    if(debug)
03307       printf("@@@@ lock on\n");
03308 
03309    res = simple_command_ft897(myrpt, 0x00);           /* LOCK on */  
03310 
03311    if(debug)
03312       printf("@@@@ ptt off\n");
03313 
03314    if(!res)
03315       res = simple_command_ft897(myrpt, 0x88);     /* PTT off */
03316 
03317    if(debug)
03318       printf("Modulation mode\n");
03319 
03320    if(!res)
03321       res = set_mode_ft897(myrpt, myrpt->remmode);    /* Modulation mode */
03322 
03323    if(debug)
03324       printf("Split off\n");
03325 
03326    if(!res)
03327       simple_command_ft897(myrpt, 0x82);        /* Split off */
03328 
03329    if(debug)
03330       printf("Frequency\n");
03331 
03332    if(!res)
03333       res = set_freq_ft897(myrpt, myrpt->freq);    /* Frequency */
03334    if((myrpt->remmode == REM_MODE_FM)){
03335       if(debug)
03336          printf("Offset\n");
03337       if(!res)
03338          res = set_offset_ft897(myrpt, myrpt->offset);   /* Offset if FM */
03339       if((!res)&&(myrpt->rxplon || myrpt->txplon)){
03340          if(debug)
03341             printf("CTCSS tone freqs.\n");
03342          res = set_ctcss_freq_ft897(myrpt, myrpt->txpl, myrpt->rxpl); /* CTCSS freqs if CTCSS is enabled */
03343       }
03344       if(!res){
03345          if(debug)
03346             printf("CTCSS mode\n");
03347          res = set_ctcss_mode_ft897(myrpt, myrpt->txplon, myrpt->rxplon); /* CTCSS mode */
03348       }
03349    }
03350    if((myrpt->remmode == REM_MODE_USB)||(myrpt->remmode == REM_MODE_LSB)){
03351       if(debug)
03352          printf("Clarifier off\n");
03353       simple_command_ft897(myrpt, 0x85);        /* Clarifier off if LSB or USB */
03354    }
03355    return res;
03356 }
03357 
03358 static int closerem_ft897(struct rpt *myrpt)
03359 {
03360    simple_command_ft897(myrpt, 0x88); /* PTT off */
03361    return 0;
03362 }  
03363 
03364 /*
03365 * Bump frequency up or down by a small amount 
03366 * Return 0 if the new frequnecy is valid, or -1 if invalid
03367 * Interval is in Hz, resolution is 10Hz 
03368 */
03369 
03370 static int multimode_bump_freq_ft897(struct rpt *myrpt, int interval)
03371 {
03372    int m,d;
03373    char mhz[MAXREMSTR], decimals[MAXREMSTR];
03374 
03375    if(debug)
03376       printf("Before bump: %s\n", myrpt->freq);
03377 
03378    if(split_freq(mhz, decimals, myrpt->freq))
03379       return -1;
03380    
03381    m = atoi(mhz);
03382    d = atoi(decimals);
03383 
03384    d += (interval / 10); /* 10Hz resolution */
03385    if(d < 0){
03386       m--;
03387       d += 100000;
03388    }
03389    else if(d >= 100000){
03390       m++;
03391       d -= 100000;
03392    }
03393 
03394    if(check_freq_ft897(m, d, NULL)){
03395       if(debug)
03396          printf("Bump freq invalid\n");
03397       return -1;
03398    }
03399 
03400    snprintf(myrpt->freq, MAXREMSTR, "%d.%05d", m, d);
03401 
03402    if(debug)
03403       printf("After bump: %s\n", myrpt->freq);
03404 
03405    return set_freq_ft897(myrpt, myrpt->freq);   
03406 }
03407 
03408 
03409 
03410 /*
03411 * Dispatch to correct I/O handler 
03412 */
03413 
03414 static int setrem(struct rpt *myrpt)
03415 {
03416    if(!strcmp(myrpt->remote, remote_rig_ft897))
03417       return set_ft897(myrpt);
03418    else if(!strcmp(myrpt->remote, remote_rig_rbi))
03419       return setrbi(myrpt);
03420    else
03421       return -1;
03422 }
03423 
03424 static int closerem(struct rpt *myrpt)
03425 {
03426    if(!strcmp(myrpt->remote, remote_rig_ft897))
03427       return closerem_ft897(myrpt);
03428    else
03429       return 0;
03430 }
03431 
03432 /*
03433 * Dispatch to correct frequency checker
03434 */
03435 
03436 static int check_freq(struct rpt *myrpt, int m, int d, int *defmode)
03437 {
03438    if(!strcmp(myrpt->remote, remote_rig_ft897))
03439       return check_freq_ft897(m, d, defmode);
03440    else if(!strcmp(myrpt->remote, remote_rig_rbi))
03441       return check_freq_rbi(m, d, defmode);
03442    else
03443       return -1;
03444 }
03445 
03446 /*
03447 * Return 1 if rig is multimode capable
03448 */
03449 
03450 static int multimode_capable(struct rpt *myrpt)
03451 {
03452    if(!strcmp(myrpt->remote, remote_rig_ft897))
03453       return 1;
03454    return 0;
03455 }  
03456 
03457 /*
03458 * Dispatch to correct frequency bumping function
03459 */
03460 
03461 static int multimode_bump_freq(struct rpt *myrpt, int interval)
03462 {
03463    if(!strcmp(myrpt->remote, remote_rig_ft897))
03464       return multimode_bump_freq_ft897(myrpt, interval);
03465    else
03466       return -1;
03467 }
03468 
03469 
03470 /*
03471 * Queue announcment that scan has been stopped 
03472 */
03473 
03474 static void stop_scan(struct rpt *myrpt, int flag)
03475 {
03476    myrpt->hfscanmode = 0;
03477    myrpt->hfscanstatus = ((flag) ? -2 : -1);
03478 }
03479 
03480 /*
03481 * This is called periodically when in scan mode
03482 */
03483 
03484 
03485 static int service_scan(struct rpt *myrpt)
03486 {
03487    int res, interval;
03488    char mhz[MAXREMSTR], decimals[MAXREMSTR], k10=0i, k100=0;
03489 
03490    switch(myrpt->hfscanmode){
03491 
03492       case HF_SCAN_DOWN_SLOW:
03493          interval = -10; /* 100Hz /sec */
03494          break;
03495 
03496       case HF_SCAN_DOWN_QUICK:
03497          interval = -50; /* 500Hz /sec */
03498          break;
03499 
03500       case HF_SCAN_DOWN_FAST:
03501          interval = -200; /* 2KHz /sec */
03502          break;
03503 
03504       case HF_SCAN_UP_SLOW:
03505          interval = 10; /* 100Hz /sec */
03506          break;
03507 
03508       case HF_SCAN_UP_QUICK:
03509          interval = 50; /* 500 Hz/sec */
03510          break;
03511 
03512       case HF_SCAN_UP_FAST:
03513          interval = 200; /* 2KHz /sec */
03514          break;
03515 
03516       default:
03517          myrpt->hfscanmode = 0; /* Huh? */
03518          return -1;
03519    }
03520 
03521    res = split_freq(mhz, decimals, myrpt->freq);
03522       
03523    if(!res){
03524       k100 =decimals[0];
03525       k10 = decimals[1];
03526       res = multimode_bump_freq(myrpt, interval);
03527    }
03528 
03529    if(!res)
03530       res = split_freq(mhz, decimals, myrpt->freq);
03531 
03532 
03533    if(res){
03534       stop_scan(myrpt,1);
03535       return -1;
03536    }
03537 
03538    /* Announce 10KHz boundaries */
03539    if(k10 != decimals[1]){
03540       int myhund = (interval < 0) ? k100 : decimals[0];
03541       int myten = (interval < 0) ? k10 : decimals[1];
03542       myrpt->hfscanstatus = (myten == '0') ? (myhund - '0') * 100 : (myten - '0') * 10;
03543    }
03544    return res;
03545 
03546 }
03547 
03548 
03549 static int rmt_telem_start(struct rpt *myrpt, struct ast_channel *chan, int delay)
03550 {
03551          myrpt->remotetx = 0;
03552          ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_UNKEY);
03553          if (!myrpt->remoterx)
03554             ast_indicate(chan,AST_CONTROL_RADIO_KEY);
03555          if (ast_safe_sleep(chan, delay) == -1)
03556                return -1;
03557          return 0;
03558 }
03559 
03560 
03561 static int rmt_telem_finish(struct rpt *myrpt, struct ast_channel *chan)
03562 {
03563 
03564 struct zt_params par;
03565 
03566    if (ioctl(myrpt->txchannel->fds[0],ZT_GET_PARAMS,&par) == -1)
03567    {
03568       return -1;
03569 
03570    }
03571    if (!par.rxisoffhook)
03572    {
03573       ast_indicate(myrpt->remchannel,AST_CONTROL_RADIO_UNKEY);
03574       myrpt->remoterx = 0;
03575    }
03576    else
03577    {
03578       myrpt->remoterx = 1;
03579    }
03580    return 0;
03581 }
03582 
03583 
03584 static int rmt_sayfile(struct rpt *myrpt, struct ast_channel *chan, int delay, char *filename)
03585 {
03586    int res;
03587 
03588    res = rmt_telem_start(myrpt, chan, delay);
03589 
03590    if(!res)
03591       res = sayfile(chan, filename);
03592    
03593    if(!res)
03594       res = rmt_telem_finish(myrpt, chan);
03595    return res;
03596 }
03597 
03598 static int rmt_saycharstr(struct rpt *myrpt, struct ast_channel *chan, int delay, char *charstr)
03599 {
03600    int res;
03601 
03602    res = rmt_telem_start(myrpt, chan, delay);
03603 
03604    if(!res)
03605       res = saycharstr(chan, charstr);
03606    
03607    if(!res)
03608       res = rmt_telem_finish(myrpt, chan);
03609    return res;
03610 }
03611 
03612 
03613 
03614 /*
03615 * Remote base function
03616 */
03617 
03618 static int function_remote(struct rpt *myrpt, char *param, char *digitbuf, int command_source, struct rpt_link *mylink)
03619 {
03620    char *s,*s1,*s2,*val;
03621    int i,j,ht,k,l,ls2,m,d,res,offset,offsave, modesave, defmode;
03622    char multimode = 0;
03623    char oc;
03624    char tmp[20], freq[20] = "", savestr[20] = "";
03625    char mhz[MAXREMSTR], decimals[MAXREMSTR];
03626    struct ast_channel *mychannel;
03627 
03628    if((!param) || (command_source == SOURCE_RPT) || (command_source == SOURCE_LNK))
03629       return DC_ERROR;
03630       
03631    multimode = multimode_capable(myrpt);
03632 
03633    mychannel = myrpt->remchannel;
03634    
03635    
03636    switch(myatoi(param)){
03637 
03638       case 1:  /* retrieve memory */
03639          if(strlen(digitbuf) < 2) /* needs 2 digits */
03640             break;
03641          
03642          for(i = 0 ; i < 2 ; i++){
03643             if((digitbuf[i] < '0') || (digitbuf[i] > '9'))
03644                return DC_ERROR;
03645          }
03646        
03647          val = ast_variable_retrieve(cfg, MEMORY, digitbuf);
03648          if (!val){
03649             if (ast_safe_sleep(mychannel,1000) == -1)
03650                return DC_ERROR;
03651             sayfile(mychannel,"rpt/memory_notfound");
03652             return DC_COMPLETE;
03653          }        
03654          strncpy(tmp,val,sizeof(tmp) - 1);
03655          s = strchr(tmp,',');
03656          if (!s)
03657             return DC_ERROR;
03658          *s++ = 0;
03659          s1 = strchr(s,',');
03660          if (!s1)
03661             return DC_ERROR;
03662          *s1++ = 0;
03663          strncpy(myrpt->freq, tmp, sizeof(myrpt->freq) - 1);
03664          strncpy(myrpt->rxpl, s, sizeof(myrpt->rxpl) - 1);
03665          strncpy(myrpt->txpl, s, sizeof(myrpt->rxpl) - 1);
03666          myrpt->remmode = REM_MODE_FM;
03667          myrpt->offset = REM_SIMPLEX;
03668          myrpt->powerlevel = REM_MEDPWR;
03669          myrpt->txplon = myrpt->rxplon = 0;
03670          while(*s1)
03671          {
03672             switch(*s1++){
03673                case 'A':
03674                case 'a':
03675                   strcpy(myrpt->rxpl, "100.0");
03676                   strcpy(myrpt->txpl, "100.0");
03677                   myrpt->remmode = REM_MODE_AM; 
03678                   break;
03679                
03680                case 'B':
03681                case 'b':
03682                   strcpy(myrpt->rxpl, "100.0");
03683                   strcpy(myrpt->txpl, "100.0");
03684                   myrpt->remmode = REM_MODE_LSB;
03685                   break;
03686          
03687                case 'F':
03688                   myrpt->remmode = REM_MODE_FM;
03689                   break;
03690 
03691                case 'L':
03692                case 'l':
03693                   myrpt->powerlevel = REM_LOWPWR;
03694                   break;               
03695                case 'H':
03696                case 'h':
03697                   myrpt->powerlevel = REM_HIPWR;
03698                   break;
03699                
03700                case 'M':
03701                case 'm':
03702                   myrpt->powerlevel = REM_MEDPWR;
03703                   break;
03704                   
03705                case '-':
03706                   myrpt->offset = REM_MINUS;
03707                   break;
03708                   
03709                case '+':
03710                   myrpt->offset = REM_PLUS;
03711                   break;
03712                   
03713                case 'S':
03714                case 's':
03715                   myrpt->offset = REM_SIMPLEX;
03716                   break;
03717                   
03718                case 'T':
03719                case 't':
03720                   myrpt->txplon = 1;
03721                   break;
03722                   
03723                case 'R':
03724                case 'r':
03725                   myrpt->rxplon = 1;
03726                   break;
03727 
03728                case 'U':
03729                case 'u':
03730                   strcpy(myrpt->rxpl, "100.0");
03731                   strcpy(myrpt->txpl, "100.0");
03732                   myrpt->remmode = REM_MODE_USB;
03733                   break;
03734             }
03735          }
03736       
03737       
03738          if (setrem(myrpt) == -1)
03739             return DC_ERROR;
03740       
03741       
03742          return DC_COMPLETE;  
03743          
03744       case 2:  /* set freq and offset */
03745       
03746          
03747             for(i = 0, j = 0, k = 0, l = 0 ; digitbuf[i] ; i++){ /* look for M+*K+*O or M+*H+* depending on mode */
03748             if(digitbuf[i] == '*'){
03749                j++;
03750                continue;
03751             }
03752             if((digitbuf[i] < '0') || (digitbuf[i] > '9'))
03753                goto invalid_freq;
03754             else{
03755                if(j == 0)
03756                   l++; /* # of digits before first * */
03757                if(j == 1)
03758                   k++; /* # of digits after first * */
03759             }
03760          }
03761       
03762          i = strlen(digitbuf) - 1;
03763          if(multimode){
03764             if((j > 2) || (l > 3) || (k > 6))
03765                goto invalid_freq; /* &^@#! */
03766          }
03767          else{
03768             if((j > 2) || (l > 4) || (k > 3))
03769                goto invalid_freq; /* &^@#! */
03770          }
03771 
03772          /* Wait for M+*K+* */
03773 
03774          if(j < 2)
03775             break; /* Not yet */
03776 
03777          /* We have a frequency */
03778 
03779          strncpy(tmp, digitbuf ,sizeof(tmp) - 1);
03780          
03781          s = tmp;
03782          s1 = strsep(&s, "*"); /* Pick off MHz */
03783          s2 = strsep(&s,"*"); /* Pick off KHz and Hz */
03784          ls2 = strlen(s2); 
03785          
03786          switch(ls2){ /* Allow partial entry of khz and hz digits for laziness support */
03787             case 1:
03788                ht = 0;
03789                k = 100 * atoi(s2);
03790                break;
03791             
03792             case 2:
03793                ht = 0;
03794                k = 10 * atoi(s2);
03795                break;
03796                
03797             case 3:
03798                if(!multimode){
03799                   if((s2[2] != '0')&&(s2[2] != '5'))
03800                      goto invalid_freq;
03801                }
03802                ht = 0;
03803                k = atoi(s2);
03804                   break;
03805             case 4:
03806                k = atoi(s2)/10;
03807                ht = 10 * (atoi(s2+(ls2-1)));
03808                break;
03809 
03810             case 5:
03811                k = atoi(s2)/100;
03812                ht = (atoi(s2+(ls2-2)));
03813                break;
03814                
03815             default:
03816                goto invalid_freq;
03817          }
03818 
03819          /* Check frequency for validity and establish a default mode */
03820          
03821          snprintf(freq, sizeof(freq), "%s.%03d%02d",s1, k, ht);
03822 
03823          if(debug)
03824             printf("New frequency: %s\n", freq);      
03825    
03826          split_freq(mhz, decimals, freq);
03827          m = atoi(mhz);
03828          d = atoi(decimals);
03829 
03830                         if(check_freq(myrpt, m, d, &defmode)) /* Check to see if frequency entered is legit */
03831                                 goto invalid_freq;
03832 
03833 
03834          if((defmode == REM_MODE_FM) && (digitbuf[i] == '*')) /* If FM, user must enter and additional offset digit */
03835             break; /* Not yet */
03836 
03837 
03838          offset = REM_SIMPLEX; /* Assume simplex */
03839 
03840          if(defmode == REM_MODE_FM){
03841             oc = *s; /* Pick off offset */
03842          
03843             if (oc){
03844                switch(oc){
03845                   case '1':
03846                      offset = REM_MINUS;
03847                      break;
03848                   
03849                   case '2':
03850                      offset = REM_SIMPLEX;
03851                   break;
03852                   
03853                   case '3':
03854                      offset = REM_PLUS;
03855                      break;
03856                   
03857                   default:
03858                      goto invalid_freq;
03859                } 
03860             } 
03861          }  
03862          offsave = myrpt->offset;
03863          modesave = myrpt->remmode;
03864          strncpy(savestr, myrpt->freq, sizeof(savestr) - 1);
03865          strncpy(myrpt->freq, freq, sizeof(myrpt->freq) - 1);
03866          myrpt->offset = offset;
03867          myrpt->remmode = defmode;
03868 
03869          if (setrem(myrpt) == -1){
03870             myrpt->offset = offsave;
03871             myrpt->remmode = modesave;
03872             strncpy(myrpt->freq, savestr, sizeof(myrpt->freq) - 1);
03873             goto invalid_freq;
03874          }
03875 
03876          return DC_COMPLETE;
03877 
03878 
03879          invalid_freq:
03880    
03881          rmt_sayfile(myrpt, mychannel, 1000, "rpt/invalid-freq");
03882 
03883          return DC_ERROR; 
03884       
03885       case 3: /* set rx PL tone */
03886          
03887             for(i = 0, j = 0, k = 0, l = 0 ; digitbuf[i] ; i++){ /* look for N+*N */
03888             if(digitbuf[i] == '*'){
03889                j++;
03890                continue;
03891             }
03892             if((digitbuf[i] < '0') || (digitbuf[i] > '9'))
03893                return DC_ERROR;
03894             else{
03895                if(j)
03896                   l++;
03897                else
03898                   k++;
03899             }
03900          }
03901          if((j > 1) || (k > 3) || (l > 1))
03902             return DC_ERROR; /* &$@^! */
03903          i = strlen(digitbuf) - 1;
03904          if((j != 1) || (k < 2)|| (l != 1))
03905             break; /* Not yet */
03906          if(debug)
03907             printf("PL digits entered %s\n", digitbuf);
03908             
03909          strncpy(tmp, digitbuf, sizeof(tmp) - 1);
03910          /* see if we have at least 1 */
03911          s = strchr(tmp,'*');
03912          if(s)
03913             *s = '.';
03914          strncpy(savestr, myrpt->rxpl, sizeof(savestr) - 1);
03915          strncpy(myrpt->rxpl, tmp, sizeof(myrpt->rxpl) - 1);
03916          
03917          if (setrem(myrpt) == -1){
03918             strncpy(myrpt->rxpl, savestr, sizeof(myrpt->rxpl) - 1);
03919             return DC_ERROR;
03920          }
03921       
03922       
03923          return DC_COMPLETE;
03924       
03925       case 4: /* set tx PL tone */
03926          
03927             for(i = 0, j = 0, k = 0, l = 0 ; digitbuf[i] ; i++){ /* look for N+*N */
03928             if(digitbuf[i] == '*'){
03929                j++;
03930                continue;
03931             }
03932             if((digitbuf[i] < '0') || (digitbuf[i] > '9'))
03933                return DC_ERROR;
03934             else{
03935                if(j)
03936                   l++;
03937                else
03938                   k++;
03939             }
03940          }
03941          if((j > 1) || (k > 3) || (l > 1))
03942             return DC_ERROR; /* &$@^! */
03943          i = strlen(digitbuf) - 1;
03944          if((j != 1) || (k < 2)|| (l != 1))
03945             break; /* Not yet */
03946          if(debug)
03947             printf("PL digits entered %s\n", digitbuf);
03948             
03949          strncpy(tmp, digitbuf, sizeof(tmp) - 1);
03950          /* see if we have at least 1 */
03951          s = strchr(tmp,'*');
03952          if(s)
03953             *s = '.';
03954          strncpy(savestr, myrpt->txpl, sizeof(savestr) - 1);
03955          strncpy(myrpt->txpl, tmp, sizeof(myrpt->txpl) - 1);
03956          
03957          if (setrem(myrpt) == -1){
03958             strncpy(myrpt->txpl, savestr, sizeof(myrpt->txpl) - 1);
03959             return DC_ERROR;
03960          }
03961       
03962       
03963          return DC_COMPLETE;
03964       
03965 
03966       case 6: /* MODE (FM,USB,LSB,AM) */
03967          if(strlen(digitbuf) < 1)
03968             break;
03969 
03970          if(!multimode)
03971             return DC_ERROR; /* Multimode radios only */
03972 
03973          switch(*digitbuf){
03974             case '1':
03975                split_freq(mhz, decimals, myrpt->freq); 
03976                m=atoi(mhz);
03977                if(m < 29) /* No FM allowed below 29MHz! */
03978                   return DC_ERROR;
03979                myrpt->remmode = REM_MODE_FM;
03980                res = rmt_saycharstr(myrpt, mychannel, 1000,"FM");
03981                break;
03982 
03983             case '2':
03984                myrpt->remmode = REM_MODE_USB;
03985                res = rmt_saycharstr(myrpt, mychannel, 1000,"USB");
03986                break;   
03987 
03988             case '3':
03989                myrpt->remmode = REM_MODE_LSB;
03990                res = rmt_saycharstr(myrpt, mychannel, 1000,"LSB");
03991                break;
03992             
03993             case '4':
03994                myrpt->remmode = REM_MODE_AM;
03995                res = rmt_saycharstr(myrpt, mychannel, 1000,"AM");
03996                break;
03997       
03998             default:
03999                return DC_ERROR;
04000          }
04001          if(res)
04002             return DC_ERROR;
04003 
04004          if(setrem(myrpt))
04005             return DC_ERROR;
04006          return DC_COMPLETE;
04007 
04008       case 100: /* other stuff */
04009       case 101: 
04010       case 102: 
04011       case 103: 
04012       case 104: 
04013       case 105: 
04014       case 106:
04015          res = rmt_telem_start(myrpt, mychannel, 1000);
04016          switch(myatoi(param)){ /* Quick commands requiring a setrem call */
04017             case 100: /* RX PL Off */
04018                myrpt->rxplon = 0;
04019                if(!res)
04020                   res = sayfile(mychannel, "rpt/rxpl");
04021                if(!res)
04022                   sayfile(mychannel, "rpt/off");
04023                break;
04024                
04025             case 101: /* RX PL On */
04026                myrpt->rxplon = 1;
04027                if(!res)
04028                   res = sayfile(mychannel, "rpt/rxpl");
04029                if(!res)
04030                   sayfile(mychannel, "rpt/on");
04031                break;
04032 
04033                
04034             case 102: /* TX PL Off */
04035                myrpt->txplon = 0;
04036                if(!res)
04037                   res = sayfile(mychannel, "rpt/txpl");
04038                if(!res)
04039                   sayfile(mychannel, "rpt/off");
04040                break;
04041                
04042             case 103: /* TX PL On */
04043                myrpt->txplon = 1;
04044                if(!res)
04045                   res = sayfile(mychannel, "rpt/txpl");
04046                if(!res)
04047                   sayfile(mychannel, "rpt/on");
04048                break;
04049                
04050             case 104: /* Low Power */
04051                myrpt->powerlevel = REM_LOWPWR;
04052                if(!res)
04053                   res = sayfile(mychannel, "rpt/lopwr");
04054                break;
04055                
04056             case 105: /* Medium Power */
04057                myrpt->powerlevel = REM_MEDPWR;
04058                if(!res)
04059                   res = sayfile(mychannel, "rpt/medpwr");
04060                break;
04061                
04062             case 106: /* Hi Power */
04063                myrpt->powerlevel = REM_HIPWR;
04064                if(!res)
04065                   res = sayfile(mychannel, "rpt/hipwr");
04066                break;
04067          
04068             default:
04069                if(!res)
04070                   rmt_telem_finish(myrpt, mychannel);
04071                return DC_ERROR;
04072          }
04073          if(!res)
04074             res = rmt_telem_finish(myrpt, mychannel);
04075          if(res)
04076             return DC_ERROR;
04077 
04078          if (setrem(myrpt) == -1) 
04079             return DC_ERROR;
04080          return DC_COMPLETE;
04081 
04082       case 107: /* Bump down 20Hz */
04083          multimode_bump_freq(myrpt, -20);
04084          return DC_COMPLETE;
04085 
04086       case 108: /* Bump down 100Hz */
04087          multimode_bump_freq(myrpt, -100);
04088          return DC_COMPLETE;
04089 
04090       case 109: /* Bump down 500Hz */
04091          multimode_bump_freq(myrpt, -500);
04092          return DC_COMPLETE;
04093 
04094       case 110: /* Bump up 20Hz */
04095          multimode_bump_freq(myrpt, 20);
04096          return DC_COMPLETE;
04097             
04098       case 111: /* Bump up 100Hz */
04099          multimode_bump_freq(myrpt, 100);
04100          return DC_COMPLETE;
04101 
04102       case 112: /* Bump up 500Hz */
04103          multimode_bump_freq(myrpt, 500);
04104          return DC_COMPLETE;
04105 
04106 
04107       case 113:
04108       case 114:
04109       case 115:
04110       case 116:
04111       case 117:
04112       case 118:
04113          myrpt->remotetx = 0;
04114          ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_UNKEY);
04115          if (!myrpt->remoterx)
04116             ast_indicate(mychannel,AST_CONTROL_RADIO_KEY);
04117          if (ast_safe_sleep(mychannel,1000) == -1)
04118                return DC_ERROR;
04119       
04120          switch(myatoi(param)){
04121 
04122             case 113: /* Scan down slow */
04123                res = sayfile(mychannel,"rpt/down");
04124                if(!res)
04125                   res = sayfile(mychannel, "rpt/slow");
04126                if(!res){
04127                   myrpt->scantimer = REM_SCANTIME;
04128                   myrpt->hfscanmode = HF_SCAN_DOWN_SLOW;
04129                }
04130                break;
04131 
04132             case 114: /* Scan down quick */
04133                res = sayfile(mychannel,"rpt/down");
04134                if(!res)
04135                   res = sayfile(mychannel, "rpt/quick");
04136                if(!res){
04137                   myrpt->scantimer = REM_SCANTIME;
04138                   myrpt->hfscanmode = HF_SCAN_DOWN_QUICK;
04139                }
04140                break;
04141 
04142             case 115: /* Scan down fast */
04143                res = sayfile(mychannel,"rpt/down");
04144                if(!res)
04145                   res = sayfile(mychannel, "rpt/fast");
04146                if(!res){
04147                   myrpt->scantimer = REM_SCANTIME;
04148                   myrpt->hfscanmode = HF_SCAN_DOWN_FAST;
04149                }
04150                break;
04151 
04152             case 116: /* Scan up slow */
04153                res = sayfile(mychannel,"rpt/up");
04154                if(!res)
04155                   res = sayfile(mychannel, "rpt/slow");
04156                if(!res){
04157                   myrpt->scantimer = REM_SCANTIME;
04158                   myrpt->hfscanmode = HF_SCAN_UP_SLOW;
04159                }
04160                break;
04161 
04162             case 117: /* Scan up quick */
04163                res = sayfile(mychannel,"rpt/up");
04164                if(!res)
04165                   res = sayfile(mychannel, "rpt/quick");
04166                if(!res){
04167                   myrpt->scantimer = REM_SCANTIME;
04168                   myrpt->hfscanmode = HF_SCAN_UP_QUICK;
04169                }
04170                break;
04171 
04172             case 118: /* Scan up fast */
04173                res = sayfile(mychannel,"rpt/up");
04174                if(!res)
04175                   res = sayfile(mychannel, "rpt/fast");
04176                if(!res){
04177                   myrpt->scantimer = REM_SCANTIME;
04178                   myrpt->hfscanmode = HF_SCAN_UP_FAST;
04179                }
04180                break;
04181          }
04182          rmt_telem_finish(myrpt,mychannel);
04183          return DC_COMPLETE;
04184 
04185 
04186       case 119: /* Tune Request */
04187          myrpt->tunerequest = 1;
04188          return DC_COMPLETE;
04189 
04190       case 5: /* Long Status */
04191       case 140: /* Short Status */
04192          res = rmt_telem_start(myrpt, mychannel, 1000);
04193 
04194          res = sayfile(mychannel,"rpt/node");
04195          if(!res)
04196             res = saycharstr(mychannel, myrpt->name);
04197          if(!res)
04198             res = sayfile(mychannel,"rpt/frequency");
04199          if(!res)
04200             res = split_freq(mhz, decimals, myrpt->freq);
04201          if(!res){
04202             m = atoi(mhz);
04203             if(m < 100)
04204                res = saynum(mychannel, m);
04205             else
04206                res = saycharstr(mychannel, mhz);
04207          }
04208          if(!res)
04209             res = sayfile(mychannel, "letters/dot");
04210          if(!res)
04211             res = saycharstr(mychannel, decimals);
04212       
04213          if(res){ 
04214             rmt_telem_finish(myrpt,mychannel);
04215             return DC_ERROR;
04216          }
04217          if(myrpt->remmode == REM_MODE_FM){ /* Mode FM? */
04218             switch(myrpt->offset){
04219    
04220                case REM_MINUS:
04221                   res = sayfile(mychannel,"rpt/minus");
04222                   break;
04223             
04224                case REM_SIMPLEX:
04225                   res = sayfile(mychannel,"rpt/simplex");
04226                   break;
04227                
04228                case REM_PLUS:
04229                   res = sayfile(mychannel,"rpt/plus");
04230                   break;
04231                
04232                default:
04233                   return DC_ERROR;
04234 
04235             }
04236          }
04237          else{ /* Must be USB, LSB, or AM */
04238             switch(myrpt->remmode){
04239 
04240                case REM_MODE_USB:
04241                   res = saycharstr(mychannel, "USB");
04242                   break;
04243 
04244                case REM_MODE_LSB:
04245                   res = saycharstr(mychannel, "LSB");
04246                   break;
04247 
04248                case REM_MODE_AM:
04249                   res = saycharstr(mychannel, "AM");
04250                   break;
04251 
04252 
04253                default:
04254                   return DC_ERROR;
04255             }
04256          }
04257 
04258          if (res == -1){
04259             rmt_telem_finish(myrpt,mychannel);
04260             return DC_ERROR;
04261          }
04262 
04263          if(myatoi(param) == 140){ /* Short status? */
04264             if(!res)
04265                res = rmt_telem_finish(myrpt, mychannel);
04266             if(res)
04267                return DC_ERROR;
04268             return DC_COMPLETE;
04269          }
04270 
04271          switch(myrpt->powerlevel){
04272 
04273             case REM_LOWPWR:
04274                res = sayfile(mychannel,"rpt/lopwr") ;
04275                break;
04276                
04277             case REM_MEDPWR:
04278                res = sayfile(mychannel,"rpt/medpwr");
04279                break;
04280             case REM_HIPWR:
04281                res = sayfile(mychannel,"rpt/hipwr"); 
04282                break;
04283          }
04284          if (res || (sayfile(mychannel,"rpt/rxpl") == -1) ||
04285             (sayfile(mychannel,"rpt/frequency") == -1) ||
04286             (saycharstr(mychannel,myrpt->rxpl) == -1) ||
04287             (sayfile(mychannel,"rpt/txpl") == -1) ||
04288             (sayfile(mychannel,"rpt/frequency") == -1) ||
04289             (saycharstr(mychannel,myrpt->txpl) == -1) ||
04290             (sayfile(mychannel,"rpt/txpl") == -1) ||
04291             (sayfile(mychannel,((myrpt->txplon) ? "rpt/on" : "rpt/off")) == -1) ||
04292             (sayfile(mychannel,"rpt/rxpl") == -1) ||
04293             (sayfile(mychannel,((myrpt->rxplon) ? "rpt/on" : "rpt/off")) == -1))
04294             {
04295                rmt_telem_finish(myrpt,mychannel);
04296                return DC_ERROR;
04297             }
04298          if(!res)
04299             res = rmt_telem_finish(myrpt,mychannel);
04300          if(res)
04301             return DC_ERROR;
04302 
04303          return DC_COMPLETE;
04304          default:
04305          return DC_ERROR;
04306    }
04307 
04308    return DC_INDETERMINATE;
04309 }
04310 
04311 static int handle_remote_dtmf_digit(struct rpt *myrpt,char c, char *keyed, int phonemode)
04312 {
04313 time_t   now;
04314 int   ret,res = 0,src;
04315 
04316    /* Stop scan mode if in scan mode */
04317    if(myrpt->hfscanmode){
04318       stop_scan(myrpt,0);
04319       return 0;
04320    }
04321 
04322    time(&now);
04323    /* if timed-out */
04324    if ((myrpt->dtmf_time_rem + DTMF_TIMEOUT) < now)
04325    {
04326       myrpt->dtmfidx = -1;
04327       myrpt->dtmfbuf[0] = 0;
04328       myrpt->dtmf_time_rem = 0;
04329    }
04330    /* if decode not active */
04331    if (myrpt->dtmfidx == -1)
04332    {
04333       /* if not lead-in digit, dont worry */
04334       if (c != myrpt->funcchar) return 0;
04335       myrpt->dtmfidx = 0;
04336       myrpt->dtmfbuf[0] = 0;
04337       myrpt->dtmf_time_rem = now;
04338       return 0;
04339    }
04340    /* if too many in buffer, start over */
04341    if (myrpt->dtmfidx >= MAXDTMF)
04342    {
04343       myrpt->dtmfidx = 0;
04344       myrpt->dtmfbuf[0] = 0;
04345       myrpt->dtmf_time_rem = now;
04346    }
04347    if (c == myrpt->funcchar)
04348    {
04349       /* if star at beginning, or 2 together, erase buffer */
04350       if ((myrpt->dtmfidx < 1) || 
04351          (myrpt->dtmfbuf[myrpt->dtmfidx - 1] == myrpt->funcchar))
04352       {
04353          myrpt->dtmfidx = 0;
04354          myrpt->dtmfbuf[0] = 0;
04355          myrpt->dtmf_time_rem = now;
04356          return 0;
04357       }
04358    }
04359    myrpt->dtmfbuf[myrpt->dtmfidx++] = c;
04360    myrpt->dtmfbuf[myrpt->dtmfidx] = 0;
04361    myrpt->dtmf_time_rem = now;
04362    
04363    
04364    src = SOURCE_RMT;
04365    if (phonemode > 1) src = SOURCE_DPHONE;
04366    else if (phonemode) src = SOURCE_PHONE;
04367    ret = collect_function_digits(myrpt, myrpt->dtmfbuf, src, NULL);
04368    
04369    switch(ret){
04370    
04371       case DC_INDETERMINATE:
04372          res = 0;
04373          break;
04374             
04375       case DC_DOKEY:
04376          if (keyed) *keyed = 1;
04377          res = 0;
04378          break;
04379             
04380       case DC_REQ_FLUSH:
04381          myrpt->dtmfidx = 0;
04382          myrpt->dtmfbuf[0] = 0;
04383          res = 0;
04384          break;
04385             
04386             
04387       case DC_COMPLETE:
04388          myrpt->dtmfbuf[0] = 0;
04389          myrpt->dtmfidx = -1;
04390          myrpt->dtmf_time_rem = 0;
04391          res = 1;
04392          break;
04393             
04394       case DC_ERROR:
04395       default:
04396          myrpt->dtmfbuf[0] = 0;
04397          myrpt->dtmfidx = -1;
04398          myrpt->dtmf_time_rem = 0;
04399          res = 0;
04400          break;
04401    }
04402 
04403    return res;
04404 }
04405 
04406 static int handle_remote_data(struct rpt *myrpt, char *str)
04407 {
04408 char  tmp[300],cmd[300],dest[300],src[300],c;
04409 int   seq,res;
04410 
04411    /* put string in our buffer */
04412    strncpy(tmp,str,sizeof(tmp) - 1);
04413    if (!strcmp(tmp,discstr)) return 0;
04414    if (sscanf(tmp,"%s %s %s %d %c",cmd,dest,src,&seq,&c) != 5)
04415    {
04416       ast_log(LOG_WARNING, "Unable to parse link string %s\n",str);
04417       return 0;
04418    }
04419    if (strcmp(cmd,"D"))
04420    {
04421       ast_log(LOG_WARNING, "Unable to parse link string %s\n",str);
04422       return 0;
04423    }
04424    /* if not for me, ignore */
04425    if (strcmp(dest,myrpt->name)) return 0;
04426    res = handle_remote_dtmf_digit(myrpt,c, NULL, 0);
04427    if (res != 1)
04428       return res;
04429    myrpt->remotetx = 0;
04430    ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_UNKEY);
04431    if (!myrpt->remoterx)
04432    {
04433       ast_indicate(myrpt->remchannel,AST_CONTROL_RADIO_KEY);
04434    }
04435    if (ast_safe_sleep(myrpt->remchannel,1000) == -1) return -1;
04436    res = telem_lookup(myrpt->remchannel, myrpt->name, "functcomplete");
04437    rmt_telem_finish(myrpt,myrpt->remchannel);
04438    return res;
04439 }
04440 
04441 static int handle_remote_phone_dtmf(struct rpt *myrpt, char c, char *keyed, int phonemode)
04442 {
04443 int   res;
04444 
04445 
04446    if (keyed && *keyed && (c == myrpt->endchar))
04447    {
04448       *keyed = 0;
04449       return DC_INDETERMINATE;
04450    }
04451 
04452    res = handle_remote_dtmf_digit(myrpt,c,keyed, phonemode);
04453    if (res != 1)
04454       return res;
04455    myrpt->remotetx = 0;
04456    ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_UNKEY);
04457    if (!myrpt->remoterx)
04458    {
04459       ast_indicate(myrpt->remchannel,AST_CONTROL_RADIO_KEY);
04460    }
04461    if (ast_safe_sleep(myrpt->remchannel,1000) == -1) return -1;
04462    res = telem_lookup(myrpt->remchannel, myrpt->name, "functcomplete");
04463    rmt_telem_finish(myrpt,myrpt->remchannel);
04464    return res;
04465 }
04466 
04467 static int attempt_reconnect(struct rpt *myrpt, struct rpt_link *l)
04468 {
04469    char *val, *s, *s1, *s2, *tele;
04470    char tmp[300], deststr[300] = "";
04471 
04472    val = ast_variable_retrieve(cfg, myrpt->nodes, l->name);
04473    if (!val)
04474    {
04475       fprintf(stderr,"attempt_reconnect: cannot find node %s\n",l->name);
04476       return -1;
04477    }
04478 
04479    ast_mutex_lock(&myrpt->lock);
04480    /* remove from queue */
04481    remque((struct qelem *) l);
04482    ast_mutex_unlock(&myrpt->lock);
04483    strncpy(tmp,val,sizeof(tmp) - 1);
04484    s = tmp;
04485    s1 = strsep(&s,",");
04486    s2 = strsep(&s,",");
04487    snprintf(deststr, sizeof(deststr), "IAX2/%s", s1);
04488    tele = strchr(deststr, '/');
04489    if (!tele) {
04490       fprintf(stderr,"attempt_reconnect:Dial number (%s) must be in format tech/number\n",deststr);
04491       return -1;
04492    }
04493    *tele++ = 0;
04494    l->elaptime = 0;
04495    l->chan = ast_request(deststr, AST_FORMAT_SLINEAR, tele,NULL);
04496    if (l->chan){
04497       ast_set_read_format(l->chan, AST_FORMAT_SLINEAR);
04498       ast_set_write_format(l->chan, AST_FORMAT_SLINEAR);
04499       l->chan->whentohangup = 0;
04500       l->chan->appl = "Apprpt";
04501       l->chan->data = "(Remote Rx)";
04502       if (option_verbose > 2)
04503          ast_verbose(VERBOSE_PREFIX_3 "rpt (attempt_reconnect) initiating call to %s/%s on %s\n",
04504             deststr, tele, l->chan->name);
04505       if(l->chan->cid.cid_num)
04506          free(l->chan->cid.cid_num);
04507       l->chan->cid.cid_num = strdup(myrpt->name);
04508                 ast_call(l->chan,tele,999); 
04509 
04510    }
04511    else 
04512    {
04513       if (option_verbose > 2)
04514          ast_verbose(VERBOSE_PREFIX_3 "Unable to place call to %s/%s on %s\n",
04515             deststr,tele,l->chan->name);
04516       return -1;
04517    }
04518    ast_mutex_lock(&myrpt->lock);
04519    /* put back in queue queue */
04520    insque((struct qelem *)l,(struct qelem *)myrpt->links.next);
04521    ast_mutex_unlock(&myrpt->lock);
04522    ast_log(LOG_NOTICE,"Reconnect Attempt to %s in process\n",l->name);
04523    return 0;
04524 }
04525 
04526 /* single thread with one file (request) to dial */
04527 static void *rpt(void *this)
04528 {
04529 struct   rpt *myrpt = (struct rpt *)this;
04530 char *tele,*idtalkover;
04531 int ms = MSWAIT,lasttx=0,val,remrx=0,identqueued,nonidentqueued,res;
04532 struct ast_channel *who;
04533 ZT_CONFINFO ci;  /* conference info */
04534 time_t   dtmf_time,t;
04535 struct rpt_link *l,*m;
04536 struct rpt_tele *telem;
04537 pthread_attr_t attr;
04538 char tmpstr[300];
04539 char cmd[MAXDTMF+1] = "";
04540 
04541 
04542    ast_mutex_lock(&myrpt->lock);
04543    strncpy(tmpstr,myrpt->rxchanname,sizeof(tmpstr) - 1);
04544    tele = strchr(tmpstr,'/');
04545    if (!tele)
04546    {
04547       fprintf(stderr,"rpt:Dial number (%s) must be in format tech/number\n",myrpt->rxchanname);
04548       ast_mutex_unlock(&myrpt->lock);
04549       myrpt->rpt_thread = AST_PTHREADT_STOP;
04550       pthread_exit(NULL);
04551    }
04552    *tele++ = 0;
04553    myrpt->rxchannel = ast_request(tmpstr,AST_FORMAT_SLINEAR,tele,NULL);
04554    if (myrpt->rxchannel)
04555    {
04556       if (myrpt->rxchannel->_state == AST_STATE_BUSY)
04557       {
04558          fprintf(stderr,"rpt:Sorry unable to obtain Rx channel\n");
04559          ast_mutex_unlock(&myrpt->lock);
04560          ast_hangup(myrpt->rxchannel);
04561          myrpt->rpt_thread = AST_PTHREADT_STOP;
04562          pthread_exit(NULL);
04563       }
04564       ast_set_read_format(myrpt->rxchannel,AST_FORMAT_SLINEAR);
04565       ast_set_write_format(myrpt->rxchannel,AST_FORMAT_SLINEAR);
04566       myrpt->rxchannel->whentohangup = 0;
04567       myrpt->rxchannel->appl = "Apprpt";
04568       myrpt->rxchannel->data = "(Repeater Rx)";
04569       if (option_verbose > 2)
04570          ast_verbose(VERBOSE_PREFIX_3 "rpt (Rx) initiating call to %s/%s on %s\n",
04571             tmpstr,tele,myrpt->rxchannel->name);
04572       ast_call(myrpt->rxchannel,tele,999);
04573       if (myrpt->rxchannel->_state != AST_STATE_UP)
04574       {
04575          ast_mutex_unlock(&myrpt->lock);
04576          ast_hangup(myrpt->rxchannel);
04577          myrpt->rpt_thread = AST_PTHREADT_STOP;
04578          pthread_exit(NULL);
04579       }
04580    }
04581    else
04582    {
04583       fprintf(stderr,"rpt:Sorry unable to obtain Rx channel\n");
04584       ast_mutex_unlock(&myrpt->lock);
04585       myrpt->rpt_thread = AST_PTHREADT_STOP;
04586       pthread_exit(NULL);
04587    }
04588    if (myrpt->txchanname)
04589    {
04590       strncpy(tmpstr,myrpt->txchanname,sizeof(tmpstr) - 1);
04591       tele = strchr(tmpstr,'/');
04592       if (!tele)
04593       {
04594          fprintf(stderr,"rpt:Dial number (%s) must be in format tech/number\n",myrpt->txchanname);
04595          ast_mutex_unlock(&myrpt->lock);
04596          ast_hangup(myrpt->rxchannel);
04597          myrpt->rpt_thread = AST_PTHREADT_STOP;
04598          pthread_exit(NULL);
04599       }
04600       *tele++ = 0;
04601       myrpt->txchannel = ast_request(tmpstr,AST_FORMAT_SLINEAR,tele,NULL);
04602       if (myrpt->txchannel)
04603       {
04604          if (myrpt->txchannel->_state == AST_STATE_BUSY)
04605          {
04606             fprintf(stderr,"rpt:Sorry unable to obtain Tx channel\n");
04607             ast_mutex_unlock(&myrpt->lock);
04608             ast_hangup(myrpt->txchannel);
04609             ast_hangup(myrpt->rxchannel);
04610             myrpt->rpt_thread = AST_PTHREADT_STOP;
04611             pthread_exit(NULL);
04612          }        
04613          ast_set_read_format(myrpt->txchannel,AST_FORMAT_SLINEAR);
04614          ast_set_write_format(myrpt->txchannel,AST_FORMAT_SLINEAR);
04615          myrpt->txchannel->whentohangup = 0;
04616          myrpt->txchannel->appl = "Apprpt";
04617          myrpt->txchannel->data = "(Repeater Tx)";
04618          if (option_verbose > 2)
04619             ast_verbose(VERBOSE_PREFIX_3 "rpt (Tx) initiating call to %s/%s on %s\n",
04620                tmpstr,tele,myrpt->txchannel->name);
04621          ast_call(myrpt->txchannel,tele,999);
04622          if (myrpt->rxchannel->_state != AST_STATE_UP)
04623          {
04624             ast_mutex_unlock(&myrpt->lock);
04625             ast_hangup(myrpt->rxchannel);
04626             ast_hangup(myrpt->txchannel);
04627             myrpt->rpt_thread = AST_PTHREADT_STOP;
04628             pthread_exit(NULL);
04629          }
04630       }
04631       else
04632       {
04633          fprintf(stderr,"rpt:Sorry unable to obtain Tx channel\n");
04634          ast_mutex_unlock(&myrpt->lock);
04635          ast_hangup(myrpt->rxchannel);
04636          myrpt->rpt_thread = AST_PTHREADT_STOP;
04637          pthread_exit(NULL);
04638       }
04639    }
04640    else
04641    {
04642       myrpt->txchannel = myrpt->rxchannel;
04643    }
04644    ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_KEY);
04645    ast_indicate(myrpt->txchannel,AST_CONTROL_RADIO_UNKEY);
04646    /* allocate a pseudo-channel thru asterisk */
04647    myrpt->pchannel = ast_request("zap",AST_FORMAT_SLINEAR,"pseudo",NULL);
04648    if (!myrpt->pchannel)
04649    {
04650       fprintf(stderr,"rpt:Sorry unable to obtain pseudo channel\n");
04651       ast_mutex_unlock(&myrpt->lock);
04652       if (myrpt->txchannel != myrpt->rxchannel) 
04653          ast_hangup(myrpt->txchannel);
04654       ast_hangup(myrpt->rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread = AST_PTHREADT_STOP;
04656       pthread_exit(NULL);
04657    }
04658    /* makructrpt.html#o61">rxchannel);
04655       myrpt->rpt_thread