scfgnet.c 42.6 KB
Newer Older
1 2 3 4
/****************************************************************************
 * @format.tab-size 4		(Plain Text/Source Code File Header)			*
 * @format.use-tabs true	(see http://www.synchro.net/ptsc_hdr.html)		*
 *																			*
5
 * Copyright Rob Swindell - http://www.synchro.net/copyright.html			*
6 7 8 9 10 11 12 13 14 15 16 17 18
 *																			*
 * This program is free software; you can redistribute it and/or			*
 * modify it under the terms of the GNU General Public License				*
 * as published by the Free Software Foundation; either version 2			*
 * of the License, or (at your option) any later version.					*
 * See the GNU General Public License for more details: gpl.txt or			*
 * http://www.fsf.org/copyleft/gpl.html										*
 *																			*
 * For Synchronet coding style and modification guidelines, see				*
 * http://www.synchro.net/source.html										*
 *																			*
 * Note: If this box doesn't appear square, then you need to fix your tabs.	*
 ****************************************************************************/
rswindell's avatar
rswindell committed
19 20

#include "scfg.h"
21

rswindell's avatar
rswindell committed
22 23 24
void qhub_edit(int num);
char *daystr(char days);
void qhub_sub_edit(uint num);
25 26 27 28 29 30 31 32 33 34 35 36 37
BOOL import_qwk_conferences(uint num);

bool new_qhub(unsigned new_qhubnum)
{
	qhub_t* new_qhub = malloc(sizeof(qhub_t));
	if(new_qhub == NULL) {
		/* ToDo: report error */
		return false;
	}
	memset(new_qhub, 0, sizeof(*new_qhub));

	qhub_t** new_qhub_list = realloc(cfg.qhub, sizeof(qhub_t*) * (cfg.total_qhubs + 1));
	if(new_qhub_list == NULL) {
38 39
		free(new_qhub);
		errormsg(WHERE, ERR_ALLOC, "qhub list", cfg.total_qhubs + 1);
40 41 42 43 44 45 46 47 48 49 50 51 52 53
		return false;
	}
	cfg.qhub = new_qhub_list;

	for(unsigned u = cfg.total_qhubs; u > new_qhubnum; u--)
		cfg.qhub[u] = cfg.qhub[u - 1];

	cfg.qhub[new_qhubnum] = new_qhub;
	cfg.total_qhubs++;
	return true;
}

bool new_qhub_sub(qhub_t* qhub, unsigned subnum, sub_t* sub, unsigned confnum)
{
54 55 56
	if((qhub->sub=realloc(qhub->sub, sizeof(*qhub->sub)*(qhub->subs+1)))==NULL
		|| (qhub->conf=(ushort *)realloc(qhub->conf, sizeof(*qhub->conf)*(qhub->subs+1)))==NULL
		|| (qhub->mode=(char *)realloc(qhub->mode, sizeof(*qhub->mode)*(qhub->subs+1)))==NULL) {
57 58 59 60 61 62 63 64 65 66 67 68 69 70 71
		/* ToDo: report error */
		return false;
	}
	for(unsigned u = qhub->subs; u > subnum; u--) {
		qhub->sub[u]=qhub->sub[u-1];
		qhub->conf[u]=qhub->conf[u-1];
		qhub->mode[u]=qhub->mode[u-1]; 
	}
	qhub->sub[subnum] = sub;
	qhub->conf[subnum] = confnum;
	qhub->mode[subnum] = qhub->misc&QHUB_CTRL_A;
	qhub->subs++;
	return true;
}

rswindell's avatar
rswindell committed
72 73 74 75 76 77 78 79
/****************************************************************************/
/* Returns the FidoNet address kept in str as ASCII.                        */
/****************************************************************************/
faddr_t atofaddr(char *str)
{
    char *p;
    faddr_t addr;

80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105
	addr.zone=addr.net=addr.node=addr.point=0;
	if((p=strchr(str,':'))!=NULL) {
		addr.zone=atoi(str);
		addr.net=atoi(p+1); 
	}
	else {
		if(cfg.total_faddrs)
			addr.zone=cfg.faddr[0].zone;
		else
			addr.zone=1;
		addr.net=atoi(str); 
	}
	if(!addr.zone)              /* no such thing as zone 0 */
		addr.zone=1;
	if((p=strchr(str,'/'))!=NULL)
		addr.node=atoi(p+1);
	else {
		if(cfg.total_faddrs)
			addr.net=cfg.faddr[0].net;
		else
			addr.net=1;
		addr.node=atoi(str); 
	}
	if((p=strchr(str,'.'))!=NULL)
		addr.point=atoi(p+1);
	return(addr);
rswindell's avatar
rswindell committed
106 107
}

108 109 110 111 112 113 114 115 116 117 118
uint getgrp(char* title)
{
	static int grp_dflt,grp_bar;
	int i;

	for(i=0;i<cfg.total_grps && i<MAX_OPTS;i++)
		sprintf(opt[i], "%-25s", cfg.grp[i]->lname);
	opt[i][0]=0;
	return uifc.list(WIN_SAV|WIN_RHT|WIN_BOT,0,0,0,&grp_dflt,&grp_bar, title, opt);
}

rswindell's avatar
rswindell committed
119
uint getsub(void)
rswindell's avatar
rswindell committed
120
{
121
	static int sub_dflt,sub_bar;
rswindell's avatar
rswindell committed
122 123 124 125
	char str[81];
	int i,j,k;
	uint subnum[MAX_OPTS+1];

126
	while(1) {
127
		i = getgrp("Select Message Group");
128 129 130 131 132 133 134 135
		if(i==-1)
			return(-1);
		for(j=k=0;j<cfg.total_subs && k<MAX_OPTS;j++)
			if(cfg.sub[j]->grp==i) {
				sprintf(opt[k],"%-25s",cfg.sub[j]->lname);
				subnum[k++]=j; 
			}
		opt[k][0]=0;
136
		sprintf(str,"Select %s Sub-board",cfg.grp[i]->sname);
137
		j=uifc.list(WIN_RHT|WIN_BOT|WIN_SAV,0,0,45,&sub_dflt,&sub_bar,str,opt);
138
		if(j==-1 || j >= cfg.total_subs)
139
			continue;
140 141
		sub_dflt++;
		sub_bar++;
142 143
		return(subnum[j]); 
	}
rswindell's avatar
rswindell committed
144 145 146 147
}

void net_cfg()
{
148 149
	static	int net_dflt,qnet_dflt,fnet_dflt,inet_dflt
			,qhub_dflt;
rswindell's avatar
rswindell committed
150 151
	char	str[81],done;
	int 	i,j,k,l;
152
	int		mode;
rswindell's avatar
rswindell committed
153

154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188
	while(1) {
		i=0;
		strcpy(opt[i++],"Internet E-mail");
		strcpy(opt[i++],"QWK Packet Networks");
		strcpy(opt[i++],"FidoNet EchoMail and NetMail");
		opt[i][0]=0;
		uifc.helpbuf=
			"`Configure Networks:`\n"
			"\n"
			"This is the network configuration menu. Select the type of network\n"
			"technology that you want to configure.\n"
		;
		i=uifc.list(WIN_ORG|WIN_ACT|WIN_CHE,0,0,0,&net_dflt,0,"Networks",opt);
		if(i==1) {	/* QWK net stuff */
			done=0;
			while(!done) {
				i=0;
				strcpy(opt[i++],"Network Hubs...");
				strcpy(opt[i++],"Default Tagline");
				opt[i][0]=0;
				uifc.helpbuf=
					"`QWK Packet Networks:`\n"
					"\n"
					"From this menu you can configure the default tagline to use for\n"
					"outgoing messages on QWK networked sub-boards, or you can select\n"
					"`Network Hubs...` to add, delete, or configure QWK hubs that your system\n"
					"calls to exchange packets with.\n"
				;
				i=uifc.list(WIN_ACT|WIN_RHT|WIN_BOT|WIN_CHE,0,0,0,&qnet_dflt,0
					,"QWK Packet Networks",opt);
				switch(i) {
					case -1:	/* ESC */
						done=1;
						break;
					case 1:
189
						uifc.helpbuf=
190
							"`QWK Network Default Tagline:`\n"
191
							"\n"
192 193 194
							"This is the default tagline to use for outgoing messages on QWK\n"
							"networked sub-boards. This default can be overridden on a per sub-board\n"
							"basis with the sub-board configuration `Network Options...`.\n"
195
						;
196
						uifc.input(WIN_MID|WIN_SAV,0,0,""
197 198 199 200 201 202 203 204 205 206 207 208
							,cfg.qnet_tagline,sizeof(cfg.qnet_tagline)-1,K_MSG|K_EDIT);
						break;
					case 0:
						while(1) {
							for(i=0;i<cfg.total_qhubs && i<MAX_OPTS;i++)
								sprintf(opt[i],"%-8.8s",cfg.qhub[i]->id);
							opt[i][0]=0;
							i=WIN_ACT|WIN_RHT|WIN_SAV;
							if(cfg.total_qhubs<MAX_OPTS)
								i|=WIN_INS|WIN_INSACT|WIN_XTR;
							if(cfg.total_qhubs)
								i|=WIN_DEL;
209
							uifc.helpbuf=
210 211 212
								"`QWK Network Hubs:`\n"
								"\n"
								"This is a list of QWK network hubs that your system calls to exchange\n"
Rob Swindell's avatar
Rob Swindell committed
213
								"message packets with.\n"
214
								"\n"
215 216 217 218 219 220
								"To add a hub, select the desired location with the arrow keys and hit\n"
								"~ INS ~.\n"
								"\n"
								"To delete a hub, select it and hit ~ DEL ~.\n"
								"\n"
								"To configure a hub, select it and hit ~ ENTER ~.\n"
221
							;
222 223 224 225 226 227 228 229 230 231 232
							i=uifc.list(i,0,0,0,&qhub_dflt,0
								,"QWK Network Hubs",opt);
							if(i==-1)
								break;
							int msk = i & MSK_ON;
							i &= MSK_OFF;
							if (msk == MSK_INS) {
								uifc.helpbuf=
									"`QWK Network Hub System ID:`\n"
									"\n"
									"This is the QWK System ID of this hub. It is used for incoming and\n"
Rob Swindell's avatar
Rob Swindell committed
233
									"outgoing network message packets and must be accurate.\n"
234 235 236 237 238 239 240
								;
								if(uifc.input(WIN_MID|WIN_SAV,0,0
									,"System ID",str,LEN_QWKID,K_UPPER)<1)
									continue;
								if(!new_qhub(i))
									continue;
								SAFECOPY(cfg.qhub[i]->id,str);
241
								SAFECOPY(cfg.qhub[i]->fmt, "ZIP");
242
								SAFECOPY(cfg.qhub[i]->call,"*qnet-ftp %s hub.address YOURPASS");
243
								cfg.qhub[i]->node = NODE_ANY;
244
								cfg.qhub[i]->days=0x7f; /* all days */
245 246
								uifc.changes=1;
								continue; 
247
							}
248 249 250 251 252 253 254 255 256 257 258 259 260 261
							if (msk == MSK_DEL) {
								free(cfg.qhub[i]->mode);
								free(cfg.qhub[i]->conf);
								free(cfg.qhub[i]->sub);
								free(cfg.qhub[i]);
								cfg.total_qhubs--;
								while(i<cfg.total_qhubs) {
									cfg.qhub[i]=cfg.qhub[i+1];
									i++; 
								}
								uifc.changes=1;
								continue; 
							}
							qhub_edit(i); 
262
						}
263 264
						break; 
				} 
265
			} 
266
		}
rswindell's avatar
rswindell committed
267

268
		else if(i==2) { 	/* FidoNet Stuff */
269
			static faddr_t savfaddr;
270 271 272
			done=0;
			while(!done) {
				i=0;
273 274 275 276 277 278 279
				tmp[0] = 0;
				for(j=0; j < cfg.total_faddrs && strlen(tmp) < 24; j++)
					sprintf(tmp + strlen(tmp), "%s%s", j ? ", " : "", smb_faddrtoa(&cfg.faddr[j], NULL));
				if(j < cfg.total_faddrs)
					strcat(tmp, ", ...");
				sprintf(opt[i++],"%-33.33s%s"
					,"System Addresses",tmp);
280
				sprintf(opt[i++],"%-33.33s%s"
281
					,"Default Origin Line", cfg.origline);
282
				sprintf(opt[i++],"%-33.33s%s"
283
					,"NetMail Semaphore",cfg.netmail_sem);
284
				sprintf(opt[i++],"%-33.33s%s"
285
					,"EchoMail Semaphore",cfg.echomail_sem);
286
				sprintf(opt[i++],"%-33.33s%s"
287
					,"NetMail Directory",cfg.netmail_dir);
288
				sprintf(opt[i++],"%-33.33s%s"
289 290
					,"Allow Sending of NetMail"
					,cfg.netmail_misc&NMAIL_ALLOW ? "Yes":"No");
291
				sprintf(opt[i++],"%-33.33s%s"
292 293
					,"Allow File Attachments"
					,cfg.netmail_misc&NMAIL_FILE ? "Yes":"No");
294
				sprintf(opt[i++],"%-33.33s%s"
295 296
					,"Send NetMail Using Alias"
					,cfg.netmail_misc&NMAIL_ALIAS ? "Yes":"No");
297
				sprintf(opt[i++],"%-33.33s%s"
298 299
					,"NetMail Defaults to Crash"
					,cfg.netmail_misc&NMAIL_CRASH ? "Yes":"No");
300
				sprintf(opt[i++],"%-33.33s%s"
301 302
					,"NetMail Defaults to Direct"
					,cfg.netmail_misc&NMAIL_DIRECT ? "Yes":"No");
303
				sprintf(opt[i++],"%-33.33s%s"
304 305
					,"NetMail Defaults to Hold"
					,cfg.netmail_misc&NMAIL_HOLD ? "Yes":"No");
306
				sprintf(opt[i++],"%-33.33s%s"
307 308
					,"Kill NetMail After Sent"
					,cfg.netmail_misc&NMAIL_KILL ? "Yes":"No");
309
				sprintf(opt[i++],"%-33.33s%"PRIu32
310
					,"Cost to Send NetMail",cfg.netmail_cost);
311 312 313 314
				if(cfg.total_faddrs > 1)
					sprintf(opt[i++],"%-33.33s%s"
						,"Choose NetMail Source Address"
						,cfg.netmail_misc&NMAIL_CHSRCADDR ? "Yes":"No");
315 316 317 318 319 320 321 322
				opt[i][0]=0;
				uifc.helpbuf=
					"`FidoNet EchoMail and NetMail:`\n"
					"\n"
					"This menu contains configuration options that pertain specifically to\n"
					"networking E-mail (NetMail) and sub-boards (EchoMail) through networks\n"
					"using FidoNet technology.\n"
				;
323
				i=uifc.list(WIN_ACT|WIN_MID|WIN_CHE,0,0,68,&fnet_dflt,0
324 325 326 327 328 329 330 331 332
					,"FidoNet EchoMail and NetMail",opt);
				switch(i) {
					case -1:	/* ESC */
						done=1;
						break;
					case 0:
						uifc.helpbuf=
							"`System FidoNet Addresses:`\n"
							"\n"
333 334 335 336 337 338
							"These are the FidoNet-style addresses of your system, used to receive\n"
							"FidoNet-style NetMail and EchoMail over FidoNet Technology Networks.\n"
							"\n"
							"The `Main` address is also used as the default address for Fido-Networked\n"
							"sub-boards (EchoMail areas).\n"
							"\n"
339
							"The supported address format (so-called 3D or 4D): `Zone`:`Net`/`Node`[.`Point`]\n"
340 341 342 343 344 345 346 347
						;
						k=l=0;
						while(1) {
							for(i=0;i<cfg.total_faddrs && i<MAX_OPTS;i++) {
								if(i==0)
									strcpy(str,"Main");
								else
									sprintf(str,"AKA %u",i);
348
								sprintf(opt[i],"%-8.8s %16s"
349
									,str,smb_faddrtoa(&cfg.faddr[i],tmp)); 
350
							}
351
							opt[i][0]=0;
352
							mode=WIN_RHT|WIN_SAV|WIN_ACT|WIN_INSACT;
353
							if(cfg.total_faddrs<MAX_OPTS)
354
								mode |= WIN_INS|WIN_XTR;
355
							if(cfg.total_faddrs)
356 357 358 359
								mode |= WIN_DEL|WIN_COPY|WIN_CUT;
							if(savfaddr.zone)
								mode |= WIN_PASTE | WIN_PASTEXTR;
							i=uifc.list(mode,0,0,0,&k,&l
360 361 362 363 364
								,"System Addresses",opt);
							if(i==-1)
								break;
							int msk = i & MSK_ON;
							i &= MSK_OFF;
365 366 367 368 369 370 371 372 373
							if (msk == MSK_INS || msk == MSK_PASTE) {
								faddr_t newfaddr;
								if(msk == MSK_INS) {
									if(uifc.input(WIN_MID|WIN_SAV,0,0,"Address (e.g. 1:2/3 or 1:2/3.4)"
										,str,25,K_UPPER) < 1)
										continue;
									newfaddr = atofaddr(str);
								} else
									newfaddr = savfaddr;
rswindell's avatar
rswindell committed
374

375 376 377 378 379 380 381 382
								if((cfg.faddr=(faddr_t *)realloc(cfg.faddr
									,sizeof(faddr_t)*(cfg.total_faddrs+1)))==NULL) {
									errormsg(WHERE,ERR_ALLOC,nulstr
										,sizeof(faddr_t)*cfg.total_faddrs+1);
									cfg.total_faddrs=0;
									bail(1);
									continue; 
								}
rswindell's avatar
rswindell committed
383

384 385 386
								for(j=cfg.total_faddrs;j>i;j--)
									cfg.faddr[j]=cfg.faddr[j-1];

387
								cfg.faddr[i]=newfaddr;
388 389 390 391
								cfg.total_faddrs++;
								uifc.changes=1;
								continue; 
							}
392 393 394 395 396 397 398
							if (msk == MSK_COPY) {
								savfaddr = cfg.faddr[i];
								continue;
							}
							if (msk == MSK_DEL || msk == MSK_CUT) {
								if(msk == MSK_CUT)
									savfaddr = cfg.faddr[i];
399 400 401 402 403 404 405 406 407
								cfg.total_faddrs--;
								while(i<cfg.total_faddrs) {
									cfg.faddr[i]=cfg.faddr[i+1];
									i++; 
								}
								uifc.changes=1;
								continue; 
							}
							smb_faddrtoa(&cfg.faddr[i],str);
408 409 410
							if(uifc.input(WIN_MID|WIN_SAV,0,0,"Address"
								,str,25,K_EDIT|K_UPPER) >= 1)
								cfg.faddr[i]=atofaddr(str); 
411 412 413 414 415 416 417 418 419 420 421 422 423
						}
						break;
					case 1:
						uifc.helpbuf=
							"`Default Origin Line:`\n"
							"\n"
							"This is the default origin line used for sub-boards networked via\n"
							"EchoMail. This origin line can be overridden on a per sub-board basis\n"
							"with the sub-board configuration `Network Options...`.\n"
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"* Origin"
							,cfg.origline,sizeof(cfg.origline)-1,K_EDIT);
						break;
424
					case 2:
425 426 427 428 429 430
						uifc.helpbuf=
							"`NetMail Semaphore File:`\n"
							"\n"
							"This is a filename that will be used as a semaphore (signal) to your\n"
							"FidoNet front-end that new NetMail has been created and the messages\n"
							"should be re-scanned.\n"
Rob Swindell's avatar
Rob Swindell committed
431
							"\n"
432
							"`Command line specifiers may be included in the semaphore filename.`\n"
Rob Swindell's avatar
Rob Swindell committed
433
							SCFG_CMDLINE_SPEC_HELP
434 435 436 437
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"NetMail Semaphore"
							,cfg.netmail_sem,sizeof(cfg.netmail_sem)-1,K_EDIT);
						break;
438
					case 3:
439 440 441 442 443 444
						uifc.helpbuf=
							"`EchoMail Semaphore File:`\n"
							"\n"
							"This is a filename that will be used as a semaphore (signal) to your\n"
							"FidoNet front-end that new EchoMail has been created and the messages\n"
							"should be re-scanned.\n"
Rob Swindell's avatar
Rob Swindell committed
445
							"\n"
446
							"`Command line specifiers may be included in the semaphore filename.`\n"
Rob Swindell's avatar
Rob Swindell committed
447
							SCFG_CMDLINE_SPEC_HELP
448 449 450 451
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"EchoMail Semaphore"
							,cfg.echomail_sem,sizeof(cfg.echomail_sem)-1,K_EDIT);
						break;
452
					case 4:
453 454 455 456 457 458 459 460 461
						uifc.helpbuf=
							"`NetMail Directory:`\n"
							"\n"
							"This is the directory where FidoNet NetMail will be imported from\n"
							"and exported to (in FTS-1, *.MSG format).\n"
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"NetMail"
							,cfg.netmail_dir,sizeof(cfg.netmail_dir)-1,K_EDIT);
						break;
462
					case 5:
Rob Swindell's avatar
Rob Swindell committed
463
						i = (cfg.netmail_misc & NMAIL_ALLOW) ? 0 : 1;
464 465 466 467 468 469 470 471 472
						uifc.helpbuf=
							"`Allow Users to Send NetMail:`\n"
							"\n"
							"If you are on a FidoNet style network and want your users to be allowed\n"
							"to send FidoNet NetMail, set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Allow Users to Send NetMail",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_ALLOW)) {
473
							uifc.changes=1;
474
							cfg.netmail_misc|=NMAIL_ALLOW; 
475
						}
476
						else if(i==1 && cfg.netmail_misc&NMAIL_ALLOW) {
477
							uifc.changes=1;
478
							cfg.netmail_misc&=~NMAIL_ALLOW; 
479
						}
480
						break;
481
					case 6:
Rob Swindell's avatar
Rob Swindell committed
482
						i = (cfg.netmail_misc & NMAIL_FILE) ? 0 : 1;
483 484 485 486 487 488 489 490 491
						uifc.helpbuf=
							"`Allow Users to Send NetMail File Attachments:`\n"
							"\n"
							"If you are on a FidoNet style network and want your users to be allowed\n"
							"to send NetMail file attachments, set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Allow Users to Send NetMail File Attachments",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_FILE)) {
492
							uifc.changes=1;
493 494 495 496 497 498
							cfg.netmail_misc|=NMAIL_FILE; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_FILE) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_FILE; 
						}
rswindell's avatar
rswindell committed
499
						break;
500
					case 7:
Rob Swindell's avatar
Rob Swindell committed
501
						i = (cfg.netmail_misc & NMAIL_ALIAS) ? 0 : 1;
502
						uifc.helpbuf=
503
							"`Use Aliases in NetMail:`\n"
504
							"\n"
505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520
							"If you allow aliases on your system and wish users to have their NetMail\n"
							"contain their alias as the `From User`, set this option to `Yes`. If you\n"
							"want all NetMail to be sent using users' real names, set this option to\n"
							"`No`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Use Aliases in NetMail",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_ALIAS)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_ALIAS; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_ALIAS) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_ALIAS; 
						}
						break;
521
					case 8:
Rob Swindell's avatar
Rob Swindell committed
522
						i = (cfg.netmail_misc & NMAIL_CRASH) ? 0 : 1;
523 524
						uifc.helpbuf=
							"`NetMail Defaults to Crash Status:`\n"
525
							"\n"
526 527 528 529 530 531 532 533 534 535 536 537 538 539
							"If you want all NetMail to default to crash (send immediately) status,\n"
							"set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"NetMail Defaults to Crash Status",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_CRASH)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_CRASH; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_CRASH) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_CRASH; 
						}
						break;
540
					case 9:
Rob Swindell's avatar
Rob Swindell committed
541
						i = (cfg.netmail_misc & NMAIL_DIRECT) ? 0 : 1;
542 543
						uifc.helpbuf=
							"`NetMail Defaults to Direct Status:`\n"
544
							"\n"
545 546 547 548 549 550 551 552 553 554 555 556 557 558
							"If you want all NetMail to default to direct (send directly) status,\n"
							"set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"NetMail Defaults to Direct Status",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_DIRECT)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_DIRECT; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_DIRECT) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_DIRECT; 
						}
						break;
559
					case 10:
Rob Swindell's avatar
Rob Swindell committed
560
						i = (cfg.netmail_misc & NMAIL_HOLD) ? 0 : 1;
561 562
						uifc.helpbuf=
							"`NetMail Defaults to Hold Status:`\n"
563
							"\n"
564 565
							"If you want all NetMail to default to hold status, set this option to\n"
							"`Yes`.\n"
566
						;
567 568 569 570 571 572 573 574 575 576 577
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"NetMail Defaults to Hold Status",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_HOLD)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_HOLD; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_HOLD) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_HOLD; 
						}
						break;
578
					case 11:
Rob Swindell's avatar
Rob Swindell committed
579
						i = (cfg.netmail_misc & NMAIL_KILL) ? 0 : 1;
580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596
						uifc.helpbuf=
							"`Kill NetMail After it is Sent:`\n"
							"\n"
							"If you want NetMail messages to be deleted after they are successfully\n"
							"sent, set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Kill NetMail After it is Sent",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_KILL)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_KILL; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_KILL) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_KILL; 
						}
						break;
597
					case 12:
598 599 600 601 602 603 604 605 606 607 608 609
						ultoa(cfg.netmail_cost,str,10);
						uifc.helpbuf=
							"`Cost in Credits to Send NetMail:`\n"
							"\n"
							"This is the number of credits it will cost your users to send NetMail.\n"
							"If you want the sending of NetMail to be free, set this value to `0`.\n"
						;
						uifc.input(WIN_MID|WIN_SAV,0,0
							,"Cost in Credits to Send NetMail"
							,str,10,K_EDIT|K_NUMBER);
						cfg.netmail_cost=atol(str);
						break; 
610
					case 13:
Rob Swindell's avatar
Rob Swindell committed
611
						i = (cfg.netmail_misc & NMAIL_CHSRCADDR) ? 0 : 1;
612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629
						uifc.helpbuf=
							"`Choose NetMail Source Address:`\n"
							"\n"
							"When the system has multiple FidoNet-style addresses, you can allow\n"
							"users to choose the source address when sending NetMail messages by\n"
							"setting this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Allow Senders of NetMail to Choose the Source Address",uifcYesNoOpts);
						if(!i && !(cfg.netmail_misc&NMAIL_CHSRCADDR)) {
							uifc.changes=1;
							cfg.netmail_misc|=NMAIL_CHSRCADDR; 
						}
						else if(i==1 && cfg.netmail_misc&NMAIL_CHSRCADDR) {
							uifc.changes=1;
							cfg.netmail_misc&=~NMAIL_CHSRCADDR; 
						}
						break;
630 631 632 633 634 635 636 637 638
				} 
			} 
		}
		else if(i==0) { 	/* Internet E-mail */
			done=0;
			while(!done) {
				i=0;
				sprintf(opt[i++],"%-27.27s%s"
					,"System Address",cfg.sys_inetaddr);
639
				sprintf(opt[i++],"%-27.27s%s"
640
					,"Inbound E-mail Semaphore",cfg.smtpmail_sem);
641
				sprintf(opt[i++],"%-27.27s%s"
642 643 644 645 646 647 648 649 650 651
					,"Outbound E-mail Semaphore",cfg.inetmail_sem);
				sprintf(opt[i++],"%-27.27s%s"
					,"Allow Sending of E-mail"
					,cfg.inetmail_misc&NMAIL_ALLOW ? "Yes":"No");
				sprintf(opt[i++],"%-27.27s%s"
					,"Allow File Attachments"
					,cfg.inetmail_misc&NMAIL_FILE ? "Yes":"No");
				sprintf(opt[i++],"%-27.27s%s"
					,"Send E-mail Using Alias"
					,cfg.inetmail_misc&NMAIL_ALIAS ? "Yes":"No");
652 653 654
				sprintf(opt[i++],"%-27.27s%s"
					,"Kill E-mail After Sent"
					,cfg.inetmail_misc&NMAIL_KILL ? "Yes":"No");
655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686
				sprintf(opt[i++],"%-27.27s%"PRIu32
					,"Cost to Send E-mail",cfg.inetmail_cost);
				opt[i][0]=0;
				uifc.helpbuf=
					"`Internet E-mail:`\n"
					"\n"
					"This menu contains configuration options that pertain specifically to\n"
					"Internet E-mail.\n"
				;
				i=uifc.list(WIN_ACT|WIN_MID|WIN_CHE,0,0,60,&inet_dflt,0
					,"Internet E-mail",opt);
				switch(i) {
					case -1:	/* ESC */
						done=1;
						break;
					case 0:
						uifc.helpbuf=
							"`Sytem Internet Address:`\n"
							"\n"
							"Enter your system's Internet address (hostname or IP address) here\n"
							"(e.g. `joesbbs.com`).\n"
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,""
							,cfg.sys_inetaddr,sizeof(cfg.sys_inetaddr)-1,K_EDIT);
						break;
					case 1:
						uifc.helpbuf=
							"`Inbound Internet E-mail Semaphore File:`\n"
							"\n"
							"This is a filename that will be used as a semaphore (signal) to any\n"
							"external Internet e-mail processors that new mail has been received\n"
							"and the message base should be re-scanned.\n"
Rob Swindell's avatar
Rob Swindell committed
687
							"\n"
688
							"`Command line specifiers may be included in the semaphore filename.`\n"
Rob Swindell's avatar
Rob Swindell committed
689
							SCFG_CMDLINE_SPEC_HELP
690 691 692 693 694 695 696 697 698 699 700
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"Inbound Semaphore"
							,cfg.smtpmail_sem,sizeof(cfg.smtpmail_sem)-1,K_EDIT);
						break;
					case 2:
						uifc.helpbuf=
							"`Outbound Internet E-mail Semaphore File:`\n"
							"\n"
							"This is a filename that will be used as a semaphore (signal) to any\n"
							"external Internet gateways (if supported) that new mail has been created\n"
							"and the message base should be re-scanned.\n"
Rob Swindell's avatar
Rob Swindell committed
701
							"\n"
702
							"`Command line specifiers may be included in the semaphore filename.`\n"
Rob Swindell's avatar
Rob Swindell committed
703
							SCFG_CMDLINE_SPEC_HELP
704 705 706 707 708
						;
						uifc.input(WIN_MID|WIN_SAV,0,0,"Outbound Semaphore"
							,cfg.inetmail_sem,sizeof(cfg.inetmail_sem)-1,K_EDIT);
						break;
					case 3:
Rob Swindell's avatar
Rob Swindell committed
709
						i = (cfg.inetmail_misc & NMAIL_ALLOW) ? 0 : 1;
710 711 712 713 714 715 716 717 718
						uifc.helpbuf=
							"`Allow Users to Send Internet E-mail:`\n"
							"\n"
							"If you want your users to be allowed to send Internet E-mail, set this\n"
							"option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Allow Users to Send E-mail",uifcYesNoOpts);
						if(!i && !(cfg.inetmail_misc&NMAIL_ALLOW)) {
719
							uifc.changes=1;
720
							cfg.inetmail_misc|=NMAIL_ALLOW; 
721
						}
722 723 724 725 726 727
						else if(i==1 && cfg.inetmail_misc&NMAIL_ALLOW) {
							uifc.changes=1;
							cfg.inetmail_misc&=~NMAIL_ALLOW; 
						}
						break;
					case 4:
Rob Swindell's avatar
Rob Swindell committed
728
						i = (cfg.inetmail_misc & NMAIL_FILE) ? 0 : 1;
729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746
						uifc.helpbuf=
							"`Allow Users to Send Internet E-mail File Attachments:`\n"
							"\n"
							"If you want your users to be allowed to send Internet E-mail with file\n"
							"attachments, set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Allow Users to Send E-mail with File Attachments",uifcYesNoOpts);
						if(!i && !(cfg.inetmail_misc&NMAIL_FILE)) {
							uifc.changes=1;
							cfg.inetmail_misc|=NMAIL_FILE; 
						}
						else if(i==1 && cfg.inetmail_misc&NMAIL_FILE) {
							uifc.changes=1;
							cfg.inetmail_misc&=~NMAIL_FILE; 
						}
						break;
					case 5:
Rob Swindell's avatar
Rob Swindell committed
747
						i = (cfg.inetmail_misc & NMAIL_ALIAS) ? 0 : 1;
748 749 750 751 752 753 754 755 756 757 758
						uifc.helpbuf=
							"`Use Aliases in Internet E-mail:`\n"
							"\n"
							"If you allow aliases on your system and wish users to have their\n"
							"Internet E-mail contain their alias as the `From User`, set this option to\n"
							"`Yes`. If you want all E-mail to be sent using users' real names, set this\n"
							"option to `No`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Use Aliases in Internet E-mail",uifcYesNoOpts);
						if(!i && !(cfg.inetmail_misc&NMAIL_ALIAS)) {
759
							uifc.changes=1;
760
							cfg.inetmail_misc|=NMAIL_ALIAS; 
761
						}
762 763 764 765 766 767
						else if(i==1 && cfg.inetmail_misc&NMAIL_ALIAS) {
							uifc.changes=1;
							cfg.inetmail_misc&=~NMAIL_ALIAS; 
						}
						break;
					case 6:
Rob Swindell's avatar
Rob Swindell committed
768
						i = (cfg.inetmail_misc & NMAIL_KILL) ? 0 : 1;
769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786
						uifc.helpbuf=
							"`Kill Internet E-mail After it is Sent:`\n"
							"\n"
							"If you want Internet E-mail messages to be deleted after they are\n"
							"successfully sent, set this option to `Yes`.\n"
						;
						i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
							,"Kill Internet E-mail After it is Sent",uifcYesNoOpts);
						if(!i && !(cfg.inetmail_misc&NMAIL_KILL)) {
							uifc.changes=1;
							cfg.inetmail_misc|=NMAIL_KILL; 
						}
						else if(i==1 && cfg.inetmail_misc&NMAIL_KILL) {
							uifc.changes=1;
							cfg.inetmail_misc&=~NMAIL_KILL;
						}
						break;
					case 7:
787 788 789 790 791 792 793 794 795 796 797 798 799 800
						ultoa(cfg.inetmail_cost,str,10);
						uifc.helpbuf=
							"`Cost in Credits to Send Internet E-mail:`\n"
							"\n"
							"This is the number of credits it will cost your users to send Internet\n"
							"E-mail. If you want the sending of Internet E-mail to be free, set this\n"
							"value to `0`.\n"
						;
						uifc.input(WIN_MID|WIN_SAV,0,0
							,"Cost in Credits to Send Internet E-mail"
							,str,10,K_EDIT|K_NUMBER);
						cfg.inetmail_cost=atol(str);
						break; 
				} 
801
			} 
802
		}
rswindell's avatar
rswindell committed
803

804 805 806 807 808
		else { /* ESC */
			i=save_changes(WIN_MID|WIN_SAV);
			if(i==-1)
				continue;
			if(!i) {
rswindell's avatar
rswindell committed
809
				save_msgs_cfg(&cfg,backup_level);
810 811 812 813
				refresh_cfg(&cfg);
			}
			break;
		}
814
	}
rswindell's avatar
rswindell committed
815 816 817 818 819 820
}

void qhub_edit(int num)
{
	static int qhub_dflt;
	char *p,done=0,str[256];
rswindell's avatar
rswindell committed
821
	int i,j;
rswindell's avatar
rswindell committed
822

823 824 825
	while(!done) {
		i=0;
		sprintf(opt[i++],"%-27.27s%s","Hub System ID",cfg.qhub[num]->id);
826
		sprintf(opt[i++],"%-27.27s%s","Archive Format",cfg.qhub[num]->fmt);
827 828 829
		sprintf(opt[i++],"%-27.27s%s","Pack Command Line",cfg.qhub[num]->pack);
		sprintf(opt[i++],"%-27.27s%s","Unpack Command Line",cfg.qhub[num]->unpack);
		sprintf(opt[i++],"%-27.27s%s","Call-out Command Line",cfg.qhub[num]->call);
830 831 832 833 834
		if(cfg.qhub[num]->node == NODE_ANY)
			SAFECOPY(str, "Any");
		else
			SAFEPRINTF(str, "%u", cfg.qhub[num]->node);
		sprintf(opt[i++],"%-27.27s%s","Call-out Node", str);
835 836 837 838 839 840 841 842 843 844 845 846
		sprintf(opt[i++],"%-27.27s%s","Call-out Days",daystr(cfg.qhub[num]->days));
		if(cfg.qhub[num]->freq) {
			sprintf(str,"%u times a day",1440/cfg.qhub[num]->freq);
			sprintf(opt[i++],"%-27.27s%s","Call-out Frequency",str); 
		}
		else {
			sprintf(str,"%2.2u:%2.2u",cfg.qhub[num]->time/60,cfg.qhub[num]->time%60);
			sprintf(opt[i++],"%-27.27s%s","Call-out Time",str); 
		}
		sprintf(opt[i++],"%-27.27s%s","Include Kludge Lines", cfg.qhub[num]->misc&QHUB_NOKLUDGES ? "No":"Yes");
		sprintf(opt[i++],"%-27.27s%s","Include VOTING.DAT File", cfg.qhub[num]->misc&QHUB_NOVOTING ? "No":"Yes");
		sprintf(opt[i++],"%-27.27s%s","Include HEADERS.DAT File", cfg.qhub[num]->misc&QHUB_NOHEADERS ? "No":"Yes");
847
		sprintf(opt[i++],"%-27.27s%s","Include UTF-8 Characters", cfg.qhub[num]->misc&QHUB_UTF8 ? "Yes":"No");
848 849 850 851 852 853 854 855 856 857 858 859 860 861
		sprintf(opt[i++],"%-27.27s%s","Extended (QWKE) Packets", cfg.qhub[num]->misc&QHUB_EXT ? "Yes":"No");
		sprintf(opt[i++],"%-27.27s%s","Exported Ctrl-A Codes"
			,cfg.qhub[num]->misc&QHUB_EXPCTLA ? "Expand" : cfg.qhub[num]->misc&QHUB_RETCTLA ? "Leave in" : "Strip");
		strcpy(opt[i++],"Import Conferences...");
		strcpy(opt[i++],"Networked Sub-boards...");
		opt[i][0]=0;
		sprintf(str,"%s QWK Network Hub",cfg.qhub[num]->id);
		uifc.helpbuf=
			"`QWK Network Hub Configuration:`\n"
			"\n"
			"This menu allows you to configure options specific to this QWKnet hub.\n"
			"\n"
			"The `Hub System ID` must match the QWK System ID of this network hub.\n"
			"\n"
862 863 864 865
			"The `Archive Format` should be set to an archive/compression format\n"
			"that the hub will expect your REP packets to be submitted with\n"
			"(typically, ZIP).\n"
			"\n"
866
			"The `Pack` and `Unpack Command Lines` are used for creating and extracting\n"
867 868
			"REP (reply) and QWK message packets using an external archive utility\n"
			"(these command-lines are optional).\n"
869 870 871 872 873 874 875 876 877 878 879 880 881 882 883
			"\n"
			"The `Call-out Command Line` is executed when your system attempts a packet\n"
			"exchange with the QWKnet hub (e.g. executes a script).\n"
			"\n"
			"`Kludge Lines` (e.g. @TZ, @VIA, @MSGID, @REPLY) provide information not\n"
			"available in standard QWK message headers, but are superfluous when the\n"
			"HEADERS.DAT file is supported and used.\n"
			"\n"
			"The `VOTING.DAT` file is the distributed QWKnet voting system supported\n"
			"in Synchronet v3.17 and later\n"
			"\n"
			"The `HEADERS.DAT` file provides all the same information that can be\n"
			"found in Kludge Lines and also addresses the 25-character QWK field\n"
			"length limits. HEADERS.DAT is supported in Synchronet v3.15 and later.\n"
			"\n"
Rob Swindell's avatar
Rob Swindell committed
884 885 886 887 888
			"Synchronet v3.18 and later supports `UTF-8` encoded messages within QWK\n"
			"packets. If the hub is using Synchronet v3.18 or later, set this option\n"
			"to `Yes`. This option also changes the QWK new-line sequence to the ASCII\n"
			"LF (10) character instead of the traditional QWK newline byte (227).\n"
			"\n"
889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911
			"`Extended (QWKE) Packets` are not normally used in QWK Networking.\n"
			"Setting this to `Yes` enables some QWKE-specific Kludge Lines that are\n"
			"superfluous when the HEADERS.DAT file is supported and used.\n"
			"\n"
			"`Exported Ctrl-A Codes` determines how Synchronet attribute/color\n"
			"codes in messages are exported into the QWK network packets. This\n"
			"may be set to `Leave in` (retain), `Expand` (to ANSI), or `Strip` (remove).\n"
			"This setting is used for QWKnet NetMail messages and may over-ride the\n"
			"equivalent setting for each sub-board.\n"
			"\n"
			"`Import Conferences...` allows you to import a QWK `control.dat` file which\n"
			"can both create new sub-boards in a target message group of your choice\n"
			"and set the `Networked Sub-boards` with QWK conference numbers correlating\n"
			"with the hub system.\n"
			"\n"
			"`Networked Sub-boards...` allows you to manually add, remove, or modify\n"
			"local sub-board associations with conferences on this QWK network hub.\n"
		;
		switch(uifc.list(WIN_ACT|WIN_MID|WIN_SAV,0,0,0,&qhub_dflt,0
			,str,opt)) {
			case -1:
				done=1;
				break;
912
			case __COUNTER__:
913
				uifc.helpbuf=
914
					"`QWK Network Hub System ID:`\n"
915
					"\n"
916 917
					"This is the QWK System ID of this hub. It is used for incoming and\n"
					"outgoing network packets and must be accurate.\n"
918
				;
919 920 921 922 923
				strcpy(str,cfg.qhub[num]->id);	/* save */
				if(!uifc.input(WIN_MID|WIN_SAV,0,0,"QWK Network Hub System ID"
					,cfg.qhub[num]->id,LEN_QWKID,K_UPPER|K_EDIT))
					strcpy(cfg.qhub[num]->id,str);
				break;
924 925 926 927 928 929 930 931 932 933 934
			case __COUNTER__:
				uifc.helpbuf=
					"`REP Packet Archive Format:`\n"
					"\n"
					"This is the archive format used for REP packets created for this QWK\n"
					"network hub (typically, this would be `ZIP`).\n"
				;
				uifc.input(WIN_MID|WIN_SAV,0,0,"REP Packet Archive Format"
					,cfg.qhub[num]->fmt,sizeof(cfg.qhub[num]->fmt)-1,K_EDIT|K_UPPER);
				break;
			case __COUNTER__:
935
				uifc.helpbuf=
936
					"`REP Packet Creation Command:`\n"
937
					"\n"
938
					"This is the command line to use to create (compress) REP packets for\n"
939
					"this QWK network hub.\n"
940
					SCFG_CMDLINE_PREFIX_HELP
Rob Swindell's avatar
Rob Swindell committed
941
					SCFG_CMDLINE_SPEC_HELP
942
				;
943 944 945
				uifc.input(WIN_MID|WIN_SAV,0,0,""
					,cfg.qhub[num]->pack,sizeof(cfg.qhub[num]->pack)-1,K_EDIT);
				break;
946
			case __COUNTER__:
947
				uifc.helpbuf=
948
					"`QWK Packet Extraction Command:`\n"
949
					"\n"
950 951
					"This is the command line to use to extract (decompress) QWK packets from\n"
					"this QWK network hub.\n"
952
					SCFG_CMDLINE_PREFIX_HELP
Rob Swindell's avatar
Rob Swindell committed
953
					SCFG_CMDLINE_SPEC_HELP
954
				;
955 956 957
				uifc.input(WIN_MID|WIN_SAV,0,0,""
					,cfg.qhub[num]->unpack,sizeof(cfg.qhub[num]->unpack)-1,K_EDIT);
				break;
958
			case __COUNTER__:
959 960 961 962 963
				uifc.helpbuf=
					"`QWK Network Hub Call-out Command Line:`\n"
					"\n"
					"This is the command line to use to initiate a call-out to this QWK\n"
					"network hub.\n"
964
					SCFG_CMDLINE_PREFIX_HELP
Rob Swindell's avatar
Rob Swindell committed
965
					SCFG_CMDLINE_SPEC_HELP
966 967 968 969
				;
				uifc.input(WIN_MID|WIN_SAV,0,0,""
					,cfg.qhub[num]->call,sizeof(cfg.qhub[num]->call)-1,K_EDIT);
				break;
970
			case __COUNTER__:
971 972 973 974
				if(cfg.qhub[num]->node == NODE_ANY)
					SAFECOPY(str, "Any");
				else
					SAFEPRINTF(str, "%u", cfg.qhub[num]->node);
975 976 977 978
				uifc.helpbuf=
					"`Node to Perform Call-out:`\n"
					"\n"
					"This is the number of the node to perform the call-out for this QWK\n"
979
					"network hub (or `Any`).\n"
980
				;
981 982
				if(uifc.input(WIN_MID|WIN_SAV,0,0
					,"Node to Perform Call-out",str,3,K_EDIT) > 0) {
983
					if(IS_DIGIT(*str))
984 985 986 987
						cfg.qhub[num]->node=atoi(str);
					else
						cfg.qhub[num]->node = NODE_ANY;
				}
988
				break;
989
			case __COUNTER__:
990 991 992 993 994 995 996 997 998 999 1000 1001 1002 1003 1004 1005 1006 1007 1008 1009
				j=0;
				while(1) {
					for(i=0;i<7;i++)
						sprintf(opt[i],"%s        %s"
							,wday[i],(cfg.qhub[num]->days&(1<<i)) ? "Yes":"No");
					opt[i][0]=0;
					uifc.helpbuf=
						"`Days to Perform Call-out:`\n"
						"\n"
						"These are the days that a call-out will be performed for this QWK\n"
						"network hub.\n"
					;
					i=uifc.list(WIN_MID,0,0,0,&j,0
						,"Days to Perform Call-out",opt);
					if(i==-1)
						break;
					cfg.qhub[num]->days^=(1<<i);
					uifc.changes=1; 
				}
				break;
1010
			case __COUNTER__:
1011 1012 1013 1014 1015 1016 1017 1018 1019 1020 1021 1022 1023 1024 1025 1026 1027 1028 1029 1030 1031 1032 1033 1034 1035 1036 1037 1038 1039 1040 1041 1042 1043 1044 1045 1046 1047 1048 1049 1050 1051 1052 1053 1054 1055 1056 1057 1058 1059 1060 1061 1062 1063
				i=1;
				uifc.helpbuf=
					"`Perform Call-out at a Specific Time:`\n"
					"\n"
					"If you want the system call this QWK network hub at a specific time,\n"
					"set this option to `Yes`. If you want the system to call this network\n"
					"hub more than once a day at predetermined intervals, set this option to\n"
					"`No`.\n"
				;
				i=uifc.list(WIN_MID|WIN_SAV,0,0,0,&i,0
					,"Perform Call-out at a Specific Time",uifcYesNoOpts);
				if(i==0) {
					sprintf(str,"%2.2u:%2.2u",cfg.qhub[num]->time/60
						,cfg.qhub[num]->time%60);
					uifc.helpbuf=
						"`Time to Perform Call-out:`\n"
						"\n"
						"This is the time (in 24 hour HH:MM format) to perform the call-out to\n"
						"this QWK network hub.\n"
					;
					if(uifc.input(WIN_MID|WIN_SAV,0,0
						,"Time to Perform Call-out (HH:MM)"
						,str,5,K_UPPER|K_EDIT)>0) {
						cfg.qhub[num]->freq=0;
						cfg.qhub[num]->time=atoi(str)*60;
						if((p=strchr(str,':'))!=NULL)
							cfg.qhub[num]->time+=atoi(p+1); 
					} 
				}
				else if(i==1) {
					sprintf(str,"%u",cfg.qhub[num]->freq
						&& cfg.qhub[num]->freq<=1440 ? 1440/cfg.qhub[num]->freq : 0);
					uifc.helpbuf=
						"`Number of Call-outs Per Day:`\n"
						"\n"
						"This is the maximum number of times the system will perform a call-out\n"
						"per day to this QWK network hub. This value is actually converted by\n"
						"Synchronet into minutes between call-outs and when the BBS is idle\n"
						"and this number of minutes since the last call-out is reached, it will\n"
						"perform a call-out.\n"
					;
					if(uifc.input(WIN_MID|WIN_SAV,0,0
						,"Number of Call-outs Per Day"
						,str,4,K_NUMBER|K_EDIT)>0) {
						cfg.qhub[num]->time=0;
						i=atoi(str);
						if(i && i<=1440)
							cfg.qhub[num]->freq=1440/i;
						else
							cfg.qhub[num]->freq=0; 
					} 
				}
				break;
1064
			case __COUNTER__:
1065 1066 1067
				cfg.qhub[num]->misc^=QHUB_NOKLUDGES;
				uifc.changes=1;
				break;
1068
			case __COUNTER__:
1069 1070 1071
				cfg.qhub[num]->misc^=QHUB_NOVOTING;
				uifc.changes=1;
				break;
1072
			case __COUNTER__:
1073 1074 1075
				cfg.qhub[num]->misc^=QHUB_NOHEADERS;
				uifc.changes=1;
				break;
1076
			case __COUNTER__:
1077
				cfg.qhub[num]->misc^=QHUB_UTF8;
1078 1079
				uifc.changes=1;
				break;
1080
			case __COUNTER__:
1081 1082 1083
				cfg.qhub[num]->misc^=QHUB_EXT;
				uifc.changes=1;
				break;
1084
			case __COUNTER__:
1085 1086 1087 1088 1089 1090 1091
				i = cfg.qhub[num]->misc&QHUB_CTRL_A;
				i++;
				if(i == QHUB_CTRL_A) i = 0;
				cfg.qhub[num]->misc &= ~QHUB_CTRL_A;
				cfg.qhub[num]->misc |= i;
				uifc.changes=1;
				break;
1092
			case __COUNTER__: