|
|
1.1 root 1: /* SMM.C */
2:
3: /* Developed 1990-1997 by Rob Swindell; PO Box 501, Yorba Linda, CA 92885 */
4:
5: /* Synchronet Match Maker */
6:
7: #include "xsdk.h"
8: #include "crc32.h"
9: #include "smmdefs.h"
10: #include "smmvars.c"
11:
12: /* RCIOLL.ASM */
13:
14: int rioini(int com,int irq); /* initialize com,irq */
15: int setbaud(int rate); /* set baud rate */
16: int rioctl(int action); /* remote i/o control */
17: int dtr(char onoff); /* set/reset dtr */
18: int outcom(int ch); /* send character */
19: int incom(void); /* receive character */
20: int ivhctl(int intcode); /* local i/o redirection */
21:
22: /************************/
23: /* Remote I/O Constants */
24: /************************/
25:
26: /* i/o mode and state flags */
27: #define CTSCK 0x1000 /* check cts (mode only) */
28: #define RTSCK 0x2000 /* check rts (mode only) */
29: #define TXBOF 0x0800 /* transmit buffer overflow (outcom only) */
30: #define ABORT 0x0400 /* check for ^C (mode), aborting (state) */
31: #define PAUSE 0x0200 /* check for ^S (mode), pausing (state) */
32: #define NOINP 0x0100 /* input buffer empty (incom only) */
33:
34: /* status flags */
35: #define RIODCD 0x80 /* DCD on */
36: #define RI 0x40 /* Ring indicate */
37: #define DSR 0x20 /* Dataset ready */
38: #define CTS 0x10 /* CTS on */
39: #define FERR 0x08 /* Frameing error */
40: #define PERR 0x04 /* Parity error */
41: #define OVRR 0x02 /* Overrun */
42: #define RXLOST 0x01 /* Receive buffer overflow */
43:
44: /* rioctl() arguments */
45: /* returns mode or state flags in high 8 bits, status flags in low 8 bits */
46:
47: /* the following return mode in high 8 bits */
48: #define IOMODE 0 /* no operation */
49: #define IOSM 1 /* i/o set mode flags */
50: #define IOCM 2 /* i/o clear mode flags */
51: /* the following return state in high 8 bits */
52: #define IOSTATE 4 /* no operation */
53: #define IOSS 5 /* i/o set state flags */
54: #define IOCS 6 /* i/o clear state flags */
55: #define IOFB 0x308 /* i/o buffer flush */
56: #define IOFI 0x208 /* input buffer flush */
57: #define IOFO 0x108 /* output buffer flush */
58: #define IOCE 9 /* i/o clear error flags */
59:
60: /* return count (16bit) */
61: #define RXBC 0x0a /* get receive buffer count */
62: #define TXBC 0x0b /* get transmit buffer count */
63: #define TXSYNC 0x0c /* sync transmition (seconds<<8|0x0c) */
64: #define IDLE 0x0d /* suspend communication routines */
65: #define RESUME 0x10d /* return from suspended state */
66: #define RLERC 0x000e /* read line error count and clear */
67: #define CPTON 0x0110 /* set input translation flag for ctrl-p on */
68: #define CPTOFF 0x0010 /* set input translation flag for ctrl-p off */
69: #define GETCPT 0x8010 /* return the status of ctrl-p translation */
70: #define MSR 0x0011 /* read modem status register */
71: #define FIFOCTL 0x0012 /* FIFO UART control */
72: #define TSTYPE 0x0013 /* Time-slice API type */
73: #define GETTST 0x8013 /* Get Time-slice API type */
74:
75:
76: #define I14DB 0x001d /* DigiBoard int 14h driver */
77: #define I14PC 0x011d /* PC int 14h driver */
78: #define I14PS 0x021d /* PS/2 int 14h driver */
79: #define I14FO 0x031d /* FOSSIL int 14h driver */
80:
81:
82: /* ivhctl() arguments */
83: #define INT29R 1 /* copy int 29h output to remote */
84: #define INT29L 2 /* Use _putlc for int 29h */
85: #define INT16 0x10 /* return remote chars to int 16h calls */
86: #define INTCLR 0 /* release int 16h, int 29h */
87:
88: #define CLREOL 256 /* Character to erase to end of line */
89: #define HIGH 8 /* High intensity for curatr */
90:
91: extern uint riobp;
92: extern int mswtyp;
93:
94: unsigned _stklen=16000; /* Set stack size in code, not header */
95:
96: int cbreakh(void); /* ctrl-break handler */
97:
98: char getage(char *birth);
99: char long_user_info(user_t user);
100: void main_user_info(user_t user);
101:
102: char *nulstr="";
103: char *wday[]={"Sun","Mon","Tue","Wed","Thu","Fri","Sat"};
104: char *mon[]={"Jan","Feb","Mar","Apr","May","Jun"
105: ,"Jul","Aug","Sep","Oct","Nov","Dec"};
106: char tmp[256],door_sys[128];
107:
108: char io_int=0;
109: struct date date;
110: struct time curtime;
111: time_t now;
112: int smm_pause=1,node_scrnlen;
113: questionnaire_t *que[5];
114: int total_ques;
115: user_t useron,tmpuser;
116: ixb_t ixb;
117: ulong useron_record,system_crc;
118: FILE *stream,*index,*trashfile;
119:
120: char *PrevReadSendQuitOrMore="\r\n\1n\1b\1h[\1cP\1b]revious screen, "
121: "[\1cR\1b]ead profile, [\1cS\1b]end telegram, [\1cQ\1b]uit, or "
122: "[\1cM\1b]ore: \1w";
123:
124: int intocm(int in)
125: {
126: return(in*2.538071);
127: }
128:
129: int cmtoin(int cm)
130: {
131: int i;
132:
133: i=cm*0.394;
134: if(((float)cm*0.394)-(float)i>=.5)
135: i++;
136: return(i);
137: }
138:
139: int kgtolp(int kg)
140: {
141: return(kg*2.2046);
142: }
143:
144: int lptokg(int lp)
145: {
146: int i;
147:
148: i=lp*0.453597;
149: if(((float)lp*0.453597)-(float)i>=.5)
150: i++;
151: return(i);
152: }
153:
154: /****************************************************************************/
155: /* Performs printf() through local assembly routines */
156: /* Called from everywhere */
157: /****************************************************************************/
158: int lprintf(char *fmat, ...) {
159: char sbuf[256];
160: int chcount;
161:
162: chcount=vsprintf(sbuf,fmat,_va_ptr);
163: lputs(sbuf);
164: return(chcount);
165: }
166:
167: /*****************************************************************************/
168: /* Returns command line generated from instr with %c replacments */
169: /*****************************************************************************/
170: char *cmdstr(char *instr, char *fpath, char *fspec, char *outstr)
171: {
172: static char static_cmd[128];
173: char str[256],str2[128],*cmd;
174: int i,j,len;
175:
176: if(outstr==NULL)
177: cmd=static_cmd;
178: else
179: cmd=outstr;
180: len=strlen(instr);
181: for(i=j=0;i<len && j<128;i++) {
182: if(instr[i]=='%') {
183: i++;
184: cmd[j]=0;
185: switch(toupper(instr[i])) {
186: case 'A': /* User alias */
187: strcat(cmd,user_name);
188: break;
189: case 'B': /* Baud (DTE) Rate */
190: strcat(cmd,ultoa(com_rate,str,10));
191: break;
192: case 'C': /* Connect Description */
193: strcat(cmd,ultoa(user_dce,str,10));
194: break;
195: case 'F': /* File path */
196: strcat(cmd,fpath);
197: break;
198: case 'G': /* Temp directory */
199: strcat(cmd,temp_dir);
200: break;
201: case 'I': /* UART IRQ Line */
202: strcat(cmd,itoa(com_irq,str,10));
203: break;
204: case 'J':
205: strcat(cmd,data_dir);
206: break;
207: case 'K':
208: strcat(cmd,ctrl_dir);
209: break;
210: case 'N': /* Node Directory (same as SBBSNODE environment var) */
211: strcat(cmd,node_dir);
212: break;
213: case 'O': /* SysOp */
214: strcat(cmd,sys_op);
215: break;
216: case 'P': /* COM Port */
217: strcat(cmd,itoa(com_port,str,10));
218: break;
219: case 'Q': /* QWK ID */
220: strcat(cmd,sys_id);
221: break;
222: case 'R': /* Rows */
223: strcat(cmd,itoa(user_rows,str,10));
224: break;
225: case 'S': /* File Spec */
226: strcat(cmd,fspec);
227: break;
228: case 'T': /* Time left in seconds */
229: strcat(cmd,itoa(time(NULL)-starttime,str,10));
230: break;
231: case 'U': /* UART I/O Address (in hex) */
232: strcat(cmd,itoa(com_base,str,16));
233: break;
234: case 'W': /* Time-slice API type (mswtype) */
235: #ifndef __OS2__
236: strcat(cmd,itoa(mswtyp,str,10));
237: #endif
238: break;
239: case '&': /* Address of msr */
240: sprintf(str,"%lu",&riobp-1);
241: strcat(cmd,str);
242: break;
243: case 'Z':
244: strcat(cmd,text_dir);
245: break;
246: case '!': /* EXEC Directory */
247: strcat(cmd,exec_dir);
248: break;
249: case '#': /* Node number (same as SBBSNNUM environment var) */
250: sprintf(str,"%d",node_num);
251: strcat(cmd,str);
252: break;
253: case '*':
254: sprintf(str,"%03d",node_num);
255: strcat(cmd,str);
256: break;
257: case '$': /* Credits */
258: strcat(cmd,ultoa(user_cdt,str,10));
259: break;
260: case '%': /* %% for percent sign */
261: strcat(cmd,"%");
262: break;
263: default: /* unknown specification */
264: if(isdigit(instr[i])) {
265: sprintf(str,"%0*d",instr[i]&0xf,user_number);
266: strcat(cmd,str); }
267: break; }
268: j=strlen(cmd); }
269: else
270: cmd[j++]=instr[i]; }
271: cmd[j]=0;
272:
273: return(cmd);
274: }
275:
276: char *base41(unsigned int i, char *str)
277: {
278: char c;
279: unsigned int j=41*41,k;
280:
281: for(c=0;c<3;c++) {
282: k=i/j;
283: str[c]='0'+k;
284: i-=(k*j);
285: j/=41;
286: if(str[c]>=':')
287: str[c]='A'+(str[c]-':');
288: if(str[c]>='[')
289: str[c]='#'+(str[c]-'['); }
290: str[c]=0;
291: return(str);
292: }
293:
294: /****************************************************************************/
295: /* Updates 16-bit "rcrc" with character 'ch' */
296: /****************************************************************************/
297: void ucrc16(uchar ch, ushort *rcrc) {
298: ushort i, cy;
299: uchar nch=ch;
300:
301: for (i=0; i<8; i++) {
302: cy=*rcrc & 0x8000;
303: *rcrc<<=1;
304: if (nch & 0x80) *rcrc |= 1;
305: nch<<=1;
306: if (cy) *rcrc ^= 0x1021; }
307: }
308:
309: /****************************************************************************/
310: /* Returns 16-crc of string (not counting terminating NULL) */
311: /****************************************************************************/
312: ushort crc16(char *str)
313: {
314: int i=0;
315: ushort crc=0;
316:
317: ucrc16(0,&crc);
318: while(str[i])
319: ucrc16(str[i++],&crc);
320: ucrc16(0,&crc);
321: ucrc16(0,&crc);
322: return(crc);
323: }
324:
325:
326: int cdt_warning(long cdt)
327: {
328: if(cdt==0)
329: return(1);
330: if(cdt>0) {
331: bprintf("\1m\1hYou will receive \1w%luk\1m in credits for this action!\r\n"
332: ,cdt/1024L);
333: return(1); }
334:
335: bprintf("\1m\1hThis action will cost you \1w%luk\1m in credits.",(-cdt)/1024L);
336: if(user_cdt+cdt_adjustment<-cdt) {
337: bprintf("\r\n\r\n\1r\1hSorry, you only have \1w%luk\1m in credits.\r\n"
338: ,(user_cdt+cdt_adjustment)/1024L);
339: return(0); }
340: return(!noyes(" Continue"));
341: }
342:
343: void adjust_cdt(long cdt)
344: {
345: if(cdt==0)
346: return;
347: cdt_adjustment+=cdt;
348: }
349:
350: int got_flags(char *req, char *got)
351: {
352: int i,j;
353:
354: for(i=0;req[i];i++) {
355: for(j=0;got[j];j++)
356: if(req[i]==got[j])
357: break;
358: if(!got[j])
359: break; }
360: if(!req[i])
361: return(1);
362: return(0);
363: }
364:
365: int can_add()
366: {
367: uchar age=getage(user_birth);
368:
369: if(user_level<min_level || (age && getage(user_birth)<min_age)
370: || !got_flags(req_flags1,user_flags1)
371: || !got_flags(req_flags2,user_flags2)
372: || !got_flags(req_flags3,user_flags3)
373: || !got_flags(req_flags4,user_flags4)
374: )
375: return(0);
376: return(1);
377: }
378:
379:
380: int trash(char *instr)
381: {
382: char str[128],word[128];
383:
384: if(!trashfile)
385: return(0);
386: strcpy(str,instr);
387: strupr(str);
388: rewind(trashfile);
389: while(!ferror(trashfile)) {
390: if(!fgets(word,125,trashfile))
391: break;
392: truncsp(word);
393: if(!word[0])
394: continue;
395: strupr(word);
396: if(strstr(str,word))
397: return(1); }
398: return(0);
399: }
400:
401: long fdate_dir(char *filespec)
402: {
403: struct ffblk f;
404: struct date fd;
405: struct time ft;
406:
407: if(findfirst(filespec,&f,FA_RDONLY|FA_HIDDEN|FA_SYSTEM|FA_DIREC)==NULL) {
408: fd.da_day=f.ff_fdate&0x1f;
409: fd.da_mon=(f.ff_fdate>>5)&0xf;
410: fd.da_year=1980+((f.ff_fdate>>9)&0x7f);
411: ft.ti_hour=(f.ff_ftime>>11)&0x1f;
412: ft.ti_min=(f.ff_ftime>>5)&0x3f;
413: ft.ti_sec=(f.ff_ftime&0xf)*2;
414: return(dostounix(&fd,&ft)); }
415: else return(NULL);
416: }
417:
418: /****************************************************************************/
419: /* Generates a 24 character ASCII string that represents the time_t pointer */
420: /* Used as a replacement for ctime() */
421: /****************************************************************************/
422: char *timestr(time_t *intime)
423: {
424: static char str[256];
425: char mer[3],hour;
426: struct tm *gm;
427:
428: gm=localtime(intime);
429: if(gm->tm_hour>=12) {
430: if(gm->tm_hour==12)
431: hour=12;
432: else
433: hour=gm->tm_hour-12;
434: strcpy(mer,"pm"); }
435: else {
436: if(gm->tm_hour==0)
437: hour=12;
438: else
439: hour=gm->tm_hour;
440: strcpy(mer,"am"); }
441: sprintf(str,"%s %s %02d %4d %02d:%02d %s"
442: ,wday[gm->tm_wday],mon[gm->tm_mon],gm->tm_mday,1900+gm->tm_year
443: ,hour,gm->tm_min,mer);
444: return(str);
445: }
446:
447:
448: void puttgram(int usernumber, char *strin)
449: {
450: char str[256];
451: int file,i;
452:
453: sprintf(str,"%4.4u.MSG",usernumber);
454: if((file=nopen(str,O_WRONLY|O_CREAT|O_APPEND))==-1) {
455: printf("\7Error opening/creating %s for creat/append access\n",str);
456: return; }
457: i=strlen(strin);
458: if(write(file,strin,i)!=i) {
459: close(file);
460: printf("\7Error writing %u bytes to %s\n",i,str);
461: return; }
462: close(file);
463: }
464:
465:
466: int send_telegram(user_t user)
467: {
468: uchar str[256],line[256],buf[1024];
469: int i;
470:
471: if(!useron.number) {
472: bputs("\r\n\1h\1rYou must create a profile first.\r\n");
473: pause();
474: return(1); }
475:
476: if(user_level<telegram_level) {
477: bputs("\r\n\1h\1rYou have insufficient access to send telegrams."
478: "\r\n");
479: pause();
480: return(1); }
481:
482: main_user_info(user);
483: CRLF;
484: if(!cdt_warning(telegram_cdt))
485: return(0);
486: if(telegram_cdt)
487: CRLF;
488: bprintf("\1n\1hSending a telegram to \1y%s\1w:\r\n\r\n"
489: ,user.name);
490: now=time(NULL);
491: memset(buf,0,512);
492: sprintf(buf,"\1n\1c\1hMatch Maker\1b telegram from \1c%s\1b "
493: "on %s:\1y\r\n"
494: ,useron.name,timestr(&now));
495: for(i=0;i<5 && !aborted;i++) {
496: bprintf("\1n\1h\1g%u of 5: \1n\1g",i+1);
497: if(!getstr(line,70,i==4 ? K_MSG:K_MSG|K_WRAP))
498: break;
499: sprintf(str,"\1n\1g%4s%s\r\n",nulstr,line);
500: strcat(buf,str); }
501: if(!i || aborted || !yesno("\r\nSave"))
502: return(0);
503: if(!(user.misc&USER_FROMSMB)) {
504: putsmsg(user.number,TGRAM_NOTICE);
505: puttgram(user.number,buf); }
506: else {
507: if((i=nopen("TELEGRAM.DAB",O_WRONLY|O_CREAT|O_APPEND|SH_DENYNO))
508: ==-1) {
509: bprintf("\r\n\1r\1h\1iError writing telegram!\r\n");
510: pause();
511: return(1); }
512: write(i,useron.system,sizeof(useron.system));
513: write(i,user.system,sizeof(user.system));
514: write(i,&user.number,sizeof(user.number));
515: write(i,buf,512);
516: close(i); }
517: adjust_cdt(telegram_cdt);
518: if(notify_user && notify_user!=user_number) {
519: sprintf(str,"\1n\1hSMM: \1y%s\1m sent a telegram to \1y%s\1m "
520: "from the Match Maker\r\n",user_name,user.name);
521: if(node_dir[0])
522: putsmsg(notify_user,str);
523: else
524: puttgram(notify_user,str); }
525: return(1);
526: }
527:
528: /****************************************************************************/
529: /* Returns 32-crc of string (not counting terminating NULL) */
530: /****************************************************************************/
531: ulong crc32(char *str)
532: {
533: int i=0;
534: ulong crc=0xffffffffUL;
535:
536: while(str[i])
537: crc=ucrc32(str[i++],crc);
538: crc=~crc;
539: return(crc);
540: }
541:
542:
543: /****************************************************************************/
544: /* Converts unix time format (long - time_t) into a char str MM/DD/YY */
545: /****************************************************************************/
546: char *unixtodstr(time_t unix, char *str)
547: {
548:
549: if(!unix)
550: strcpy(str,"00/00/00");
551: else {
552: unixtodos(unix,&date,&curtime);
553: if((unsigned)date.da_mon>12) { /* DOS leap year bug */
554: date.da_mon=1;
555: date.da_year++; }
556: if((unsigned)date.da_day>31)
557: date.da_day=1;
558: sprintf(str,"%02u/%02u/%02u",date.da_mon,date.da_day
559: ,date.da_year>=2000 ? date.da_year-2000 : date.da_year-1900); }
560: return(str);
561: }
562:
563: /****************************************************************************/
564: /* Converts a date string in format MM/DD/YY into unix time format */
565: /****************************************************************************/
566: time_t dstrtounix(char *str)
567: {
568:
569: if(!strcmp(str,"00/00/00") || !str[0])
570: return(NULL);
571: curtime.ti_hour=curtime.ti_min=curtime.ti_sec=0;
572: if(str[6]<'7')
573: date.da_year=2000+((str[6]&0xf)*10)+(str[7]&0xf);
574: else
575: date.da_year=1900+((str[6]&0xf)*10)+(str[7]&0xf);
576: date.da_mon=((str[0]&0xf)*10)+(str[1]&0xf);
577: date.da_day=((str[3]&0xf)*10)+(str[4]&0xf);
578: return(dostounix(&date,&curtime));
579: }
580:
581: /****************************************************************************/
582: /* Returns the age derived from the string 'birth' in the format MM/DD/YY */
583: /****************************************************************************/
584: char getage(char *birth)
585: {
586: char age;
587:
588: if(birth[0]<=SP)
589: return(0);
590: getdate(&date);
591: age=(date.da_year-1900)-(((birth[6]&0xf)*10)+(birth[7]&0xf));
592: if(atoi(birth)>12 || atoi(birth+3)>31)
593: return(0);
594: if(((birth[0]&0xf)*10)+(birth[1]&0xf)>date.da_mon ||
595: (((birth[0]&0xf)*10)+(birth[1]&0xf)==date.da_mon &&
596: ((birth[3]&0xf)*10)+(birth[4]&0xf)>date.da_day))
597: age--;
598: if(age<0)
599: return(0);
600: return(age);
601: }
602:
603: char marital_ch(char user_marital)
604: {
605: switch(user_marital) {
606: case MARITAL_SINGLE:
607: return('S');
608: case MARITAL_DIVORCED:
609: return('D');
610: case MARITAL_MARRIED:
611: return('M');
612: case MARITAL_WIDOWED:
613: return('W');
614: case MARITAL_OTHER:
615: return('O'); }
616: if(user_marital)
617: return('*');
618: return(SP);
619: }
620:
621: char race_ch(char user_race)
622: {
623: switch(user_race) {
624: case RACE_WHITE:
625: return('W');
626: case RACE_BLACK:
627: return('B');
628: case RACE_HISPANIC:
629: return('H');
630: case RACE_AMERINDIAN:
631: return('I');
632: case RACE_ASIAN:
633: return('A');
634: case RACE_MIDEASTERN:
635: return('M');
636: case RACE_OTHER:
637: return('O'); }
638: if(user_race)
639: return('*');
640: return(SP);
641: }
642:
643: char *hair(char user_hair)
644: {
645: switch(user_hair) {
646: case HAIR_BLONDE:
647: return("BLN");
648: case HAIR_BROWN:
649: return("BRN");
650: case HAIR_RED:
651: return("RED");
652: case HAIR_BLACK:
653: return("BLK");
654: case HAIR_GREY:
655: return("GRY");
656: case HAIR_OTHER:
657: return("OTH"); }
658: if(user_hair)
659: return("*");
660: return(nulstr);
661: }
662:
663: char *eyes(char user_eyes)
664: {
665: switch(user_eyes) {
666: case EYES_BLUE:
667: return("BLU");
668: case EYES_BROWN:
669: return("BRN");
670: case EYES_GREEN:
671: return("GRN");
672: case EYES_HAZEL:
673: return("HAZ");
674: case EYES_OTHER:
675: return("OTH"); }
676: if(user_eyes)
677: return("*");
678: return(nulstr);
679: }
680:
681: char *marital(char user_marital)
682: {
683: switch(user_marital) {
684: case MARITAL_SINGLE:
685: return("Single");
686: case MARITAL_MARRIED:
687: return("Married");
688: case MARITAL_DIVORCED:
689: return("Divorced");
690: case MARITAL_WIDOWED:
691: return("Widowed");
692: case MARITAL_OTHER:
693: return("Other"); }
694: if(user_marital)
695: return("*");
696: return(nulstr);
697: }
698:
699: char *race(char user_race)
700: {
701: switch(user_race) {
702: case RACE_WHITE:
703: return("White");
704: case RACE_BLACK:
705: return("Black");
706: case RACE_HISPANIC:
707: return("Hispanic");
708: case RACE_ASIAN:
709: return("Asian");
710: case RACE_AMERINDIAN:
711: return("American Indian");
712: case RACE_MIDEASTERN:
713: return("Middle Eastern");
714: case RACE_OTHER:
715: return("Other"); }
716: if(user_race)
717: return("*");
718: return(nulstr);
719: }
720:
721: ushort getzodiac(char *birth)
722: {
723: if((!strncmp(birth,"03",2) && atoi(birth+3)>=21)
724: || (!strncmp(birth,"04",2) && atoi(birth+3)<=19))
725: return(ZODIAC_ARIES);
726: if((!strncmp(birth,"04",2) && atoi(birth+3)>=20)
727: || (!strncmp(birth,"05",2) && atoi(birth+3)<=20))
728: return(ZODIAC_TAURUS);
729: if((!strncmp(birth,"05",2) && atoi(birth+3)>=21)
730: || (!strncmp(birth,"06",2) && atoi(birth+3)<=20))
731: return(ZODIAC_GEMINI);
732: if((!strncmp(birth,"06",2) && atoi(birth+3)>=21)
733: || (!strncmp(birth,"07",2) && atoi(birth+3)<=22))
734: return(ZODIAC_CANCER);
735: if((!strncmp(birth,"07",2) && atoi(birth+3)>=23)
736: || (!strncmp(birth,"08",2) && atoi(birth+3)<=22))
737: return(ZODIAC_LEO);
738: if((!strncmp(birth,"08",2) && atoi(birth+3)>=23)
739: || (!strncmp(birth,"09",2) && atoi(birth+3)<=22))
740: return(ZODIAC_VIRGO);
741: if((!strncmp(birth,"09",2) && atoi(birth+3)>=23)
742: || (!strncmp(birth,"10",2) && atoi(birth+3)<=22))
743: return(ZODIAC_LIBRA);
744: if((!strncmp(birth,"10",2) && atoi(birth+3)>=23)
745: || (!strncmp(birth,"11",2) && atoi(birth+3)<=21))
746: return(ZODIAC_SCORPIO);
747: if((!strncmp(birth,"11",2) && atoi(birth+3)>=22)
748: || (!strncmp(birth,"12",2) && atoi(birth+3)<=21))
749: return(ZODIAC_SAGITTARIUS);
750: if((!strncmp(birth,"12",2) && atoi(birth+3)>=22)
751: || (!strncmp(birth,"01",2) && atoi(birth+3)<=19))
752: return(ZODIAC_CAPRICORN);
753: if((!strncmp(birth,"01",2) && atoi(birth+3)>=20)
754: || (!strncmp(birth,"02",2) && atoi(birth+3)<=18))
755: return(ZODIAC_AQUARIUS);
756: if((!strncmp(birth,"02",2) && atoi(birth+3)>=19)
757: || (!strncmp(birth,"03",2) && atoi(birth+3)<=20))
758: return(ZODIAC_PISCES);
759: return(0xff);
760: }
761:
762: char *zodiac(short user_zodiac)
763: {
764: switch(user_zodiac)
765: {
766: case ZODIAC_ARIES:
767: return("Aries");
768: case ZODIAC_TAURUS:
769: return("Taurus");
770: case ZODIAC_GEMINI:
771: return("Gemini");
772: case ZODIAC_CANCER:
773: return("Cancer");
774: case ZODIAC_LEO:
775: return("Leo");
776: case ZODIAC_VIRGO:
777: return("Virgo");
778: case ZODIAC_LIBRA:
779: return("Libra");
780: case ZODIAC_SCORPIO:
781: return("Scorpio");
782: case ZODIAC_SAGITTARIUS:
783: return("Sagittarius");
784: case ZODIAC_CAPRICORN:
785: return("Capricorn");
786: case ZODIAC_AQUARIUS:
787: return("Aquarius");
788: case ZODIAC_PISCES:
789: return("Pisces"); }
790: return(nulstr);
791: }
792:
793: short ans2bits(char *str)
794: {
795: int i,j;
796: ushort bits=0;
797:
798: j=strlen(str);
799: for(i=0;i<j;i++) {
800: if(str[i]=='*')
801: return(0xffff);
802: bits|=(1<<str[i]-'A'); }
803: return(bits);
804: }
805:
806: uchar ans2uchar(char *str)
807: {
808: int i,j;
809: uchar bits=0;
810:
811: j=strlen(str);
812: for(i=0;i<j;i++) {
813: if(str[i]=='*')
814: return(0xff);
815: bits|=(1<<str[i]-'A'); }
816: return(bits);
817: }
818:
819:
820: void bits2ans(ushort bits, char *str)
821: {
822: char tmp[25];
823: int i;
824:
825: str[0]=0;
826: if(bits==0xffff) {
827: strcpy(str,"*");
828: return; }
829: for(i=0;i<16;i++)
830: if(bits&(1<<i)) {
831: tmp[0]='A'+i;
832: tmp[1]=0;
833: strcat(str,tmp); }
834: }
835:
836: void bits2str(ushort user, char *str)
837: {
838: int i;
839:
840: str[0]=0;
841: if(user==0xffff) {
842: strcpy(str,"*");
843: return; }
844: for(i=0;i<16;i++)
845: if(user&(1<<i))
846: str[i]='A'+i;
847: else
848: str[i]=SP;
849: str[i]=0;
850: }
851:
852: void uchar2ans(uchar bits, char *str)
853: {
854: char tmp[25];
855: int i;
856:
857: str[0]=0;
858: if(bits==0xff) {
859: strcpy(str,"*");
860: return; }
861: for(i=0;i<8;i++)
862: if(bits&(1<<i)) {
863: tmp[0]='A'+i;
864: tmp[1]=0;
865: strcat(str,tmp); }
866: }
867:
868: int basic_match(user_t user, user_t mate)
869: {
870: int max=0,match=0,age=getage(mate.birth),zodiac=getzodiac(mate.birth);
871:
872: if(user.pref_sex!='*' && user.pref_sex!=mate.sex
873: && !(user.misc&USER_FRIEND))
874: return(0);
875:
876: if(zodiac&user.pref_zodiac) match++;
877: else if(user.misc&USER_REQZODIAC)
878: return(0);
879: if(zodiac==user.pref_zodiac) match++;
880: max+=2;
881:
882: if(stricmp(mate.zipcode,user.min_zipcode)>=0
883: && stricmp(mate.zipcode,user.max_zipcode)<=0) match+=2;
884: else if(user.misc&USER_REQZIP) return(0);
885: max+=2;
886:
887: if(mate.marital&user.pref_marital) match++;
888: else if(user.misc&USER_REQMARITAL)
889: return(0);
890: if(mate.marital==user.pref_marital) match++;
891: max+=2;
892:
893: if(mate.race&user.pref_race) match++;
894: else if(user.misc&USER_REQRACE)
895: return(0);
896: if(mate.race==user.pref_race) match++;
897: max+=2;
898:
899: if(mate.hair&user.pref_hair) match++;
900: else if(user.misc&USER_REQHAIR)
901: return(0);
902: if(mate.hair==user.pref_hair) match++;
903: max+=2;
904:
905: if(mate.eyes&user.pref_eyes) match++;
906: else if(user.misc&USER_REQEYES)
907: return(0);
908: if(mate.eyes==user.pref_eyes) match++;
909: max+=2;
910:
911: if(age>=user.min_age
912: && (!user.max_age || age<=user.max_age)) match+=2;
913: else {
914: if(user.misc&USER_REQAGE) return(0);
915: if(age<user.min_age-((user.max_age-user.min_age)/2)
916: || (user.max_age && age>user.max_age+((user.max_age-user.min_age)/2)))
917: match-=4;
918: else if(age<user.min_age-((user.max_age-user.min_age)/3)
919: || (user.max_age && age>user.max_age+((user.max_age-user.min_age)/3)))
920: match-=3;
921: else if(age<user.min_age-((user.max_age-user.min_age)/4)
922: || (user.max_age && age>user.max_age+((user.max_age-user.min_age)/4)))
923: match-=2;
924: else if(age<user.min_age-((user.max_age-user.min_age)/5)
925: || (user.max_age && age>user.max_age+((user.max_age-user.min_age)/5)))
926: match--; }
927:
928: max+=2;
929:
930: if(mate.weight>=user.min_weight
931: && (!user.max_weight || mate.weight<=user.max_weight)) match+=2;
932: else {
933: if(user.misc&USER_REQWEIGHT) return(0);
934: if(mate.weight<user.min_weight-((user.max_weight-user.min_weight)/2)
935: || (user.max_weight
936: && mate.weight>user.max_weight+((user.max_weight-user.min_weight)/2)))
937: match-=4;
938: else if(mate.weight<user.min_weight-((user.max_weight-user.min_weight)/3)
939: || (user.max_weight
940: && mate.weight>user.max_weight+((user.max_weight-user.min_weight)/3)))
941: match-=3;
942: else if(mate.weight<user.min_weight-((user.max_weight-user.min_weight)/4)
943: || (user.max_weight
944: && mate.weight>user.max_weight+((user.max_weight-user.min_weight)/4)))
945: match-=2;
946: else if(mate.weight<user.min_weight-((user.max_weight-user.min_weight)/5)
947: || (user.max_weight
948: && mate.weight>user.max_weight+((user.max_weight-user.min_weight)/5)))
949: match--; }
950: max+=2;
951:
952: if(mate.height>=user.min_height
953: && (!user.max_height || mate.height<=user.max_height)) match+=2;
954: else {
955: if(user.misc&USER_REQHEIGHT) return(0);
956: if(mate.height<user.min_height-((user.max_height-user.min_height)/2)
957: || (user.max_height
958: && mate.height>user.max_height+((user.max_height-user.min_height)/2)))
959: match-=4;
960: else if(mate.height<user.min_height-((user.max_height-user.min_height)/3)
961: || (user.max_height
962: && mate.height>user.max_height+((user.max_height-user.min_height)/3)))
963: match-=3;
964: else if(mate.height<user.min_height-((user.max_height-user.min_height)/4)
965: || (user.max_height
966: && mate.height>user.max_height+((user.max_height-user.min_height)/4)))
967: match-=2;
968: else if(mate.height<user.min_height-((user.max_height-user.min_height)/5)
969: || (user.max_height
970: && mate.height>user.max_height+((user.max_height-user.min_height)/5)))
971: match--; }
972: max+=2;
973:
974: if(mate.income>=user.min_income
975: && (!user.max_income || mate.income==0xffffffffUL
976: || mate.income<=user.max_income)) match++;
977: else {
978: if(user.misc&USER_REQINCOME) return(0);
979: if(mate.income<user.min_income-((user.max_income-user.min_income)/2)
980: || (user.max_income
981: && mate.income>user.max_income+((user.max_income-user.min_income)/2)))
982: match-=4;
983: else if(mate.income<user.min_income-((user.max_income-user.min_income)/3)
984: || (user.max_income
985: && mate.income>user.max_income+((user.max_income-user.min_income)/3)))
986: match-=3;
987: else if(mate.income<user.min_income-((user.max_income-user.min_income)/4)
988: || (user.max_income
989: && mate.income>user.max_income+((user.max_income-user.min_income)/4)))
990: match-=2;
991: else if(mate.income<user.min_income-((user.max_income-user.min_income)/5)
992: || (user.max_income
993: && mate.income>user.max_income+((user.max_income-user.min_income)/5)))
994: match--; }
995: max++;
996:
997: if(match<=0)
998: return(0);
999:
1000: return(((float)match/max)*100.0);
1001: }
1002:
1003: int sys_quenum(char *name)
1004: {
1005: int i;
1006:
1007: for(i=0;i<total_ques;i++)
1008: if(!stricmp(que[i]->name,name))
1009: break;
1010: if(i<total_ques)
1011: return(i);
1012: return(-1);
1013: }
1014:
1015: int user_quenum(char *name, user_t user)
1016: {
1017: int i;
1018:
1019: for(i=0;i<5;i++)
1020: if(!stricmp(user.queans[i].name,name))
1021: break;
1022: if(i<5)
1023: return(i);
1024: return(-1);
1025: }
1026:
1027: int total_match(user_t user, user_t mate)
1028: {
1029: int i,j,s,u,match1,match2,quematches=0,quemax=0,quematch;
1030:
1031: match1=basic_match(user,mate);
1032: if(!match1) return(0);
1033: match2=basic_match(mate,user);
1034: if(!match2) return(0);
1035:
1036: for(i=0;i<5;i++) {
1037: if(!user.queans[i].name[0])
1038: continue;
1039: s=sys_quenum(user.queans[i].name);
1040: if(s==-1)
1041: continue;
1042: u=user_quenum(user.queans[i].name,mate);
1043: if(u==-1)
1044: continue;
1045: for(j=0;j<que[s]->total_ques;j++) {
1046: if(user.queans[u].pref[j]&mate.queans[i].self[j]) quematches+=4;
1047: if(user.queans[u].pref[j]==mate.queans[i].self[j]) quematches+=2;
1048: if(user.queans[u].self[j]&mate.queans[i].pref[j]) quematches+=2;
1049: if(user.queans[u].self[j]==mate.queans[i].pref[j]) quematches++;
1050: quemax+=9; } }
1051:
1052: if(!quemax) /* no questionnaires in common */
1053: return((match1+match1+match1+match1+match2+match2)/6);
1054:
1055: quematch=((float)quematches/quemax)*100.0;
1056: return((match1+match1+match1+match1+match2+match2+quematch)/7);
1057: }
1058:
1059:
1060: void main_user_info(user_t user)
1061: {
1062: char str[128],min[64],max[64];
1063: int i;
1064:
1065: attr(LIGHTGRAY);
1066: cls();
1067: if(SYSOP)
1068: bprintf("\1n\1gReal: \1h%.25s #%lu (%.40s)\r\n"
1069: ,user.realname,user.number,user.system);
1070: bprintf("\1n\1gName: \1h%-25.25s \1b%-10s \1c%-15s \1m%s\r\n"
1071: ,user.name
1072: ,marital(user.marital),race(user.race)
1073: ,user.sex=='M' ? "Male":"Female");
1074: if(smm_misc&SMM_METRIC)
1075: sprintf(str," %-4u",intocm(user.height));
1076: else
1077: sprintf(str,"%2u'%-2u",user.height/12,user.height%12);
1078: bprintf("\1n\1gHair: \1h%3s \1n\1gEyes: \1h%3s \1n\1gHeight:"
1079: "\1h%s \1n\1gWeight: \1h%-3u \1n\1gAge: \1h%-3u "
1080: "\1n\1gZodiac: \1h%s\r\n"
1081: ,hair(user.hair),eyes(user.eyes),str
1082: ,smm_misc&SMM_METRIC ? lptokg(user.weight) : user.weight
1083: ,getage(user.birth),zodiac(getzodiac(user.birth)));
1084: bprintf("\1n\1gFrom: \1h%-30.30s \1n\1gZip: \1h%-10.10s "
1085: "\1n\1gIncome: \1h$%sK\1n\1g/year\r\n"
1086: ,user.location,user.zipcode
1087: ,user.income==0xffffffffUL ? "?":ultoa(user.income/1000UL,tmp,10));
1088: if(smm_misc&SMM_METRIC) {
1089: sprintf(min,"%u",intocm(user.min_height));
1090: sprintf(max,"%u",intocm(user.max_height)); }
1091: else {
1092: sprintf(min,"%u'%u",user.min_height/12,user.min_height%12);
1093: sprintf(max,"%u'%u",user.max_height/12,user.max_height%12); }
1094: bprintf("\1n\1gPref: \1h\1%c%c\1%c%c\1m%c \1%c%3u\1n\1g-\1h\1%c%u\1n\1h "
1095: "\1%c%s \1n\1ghair \1h\1%c%s \1n\1geyes \1h\1%c%s\1n\1g-\1h\1%c%s "
1096: "\1%c%u\1n\1g-\1h\1%c%u\1n\1glbs \1h\1%c$%luK\1n\1g-\1h\1%c%luK\1n\1%c "
1097: "\1h%.3s\r\n"
1098: ,user.misc&USER_REQMARITAL ? 'w':'b'
1099: ,marital_ch(user.pref_marital)
1100: ,user.misc&USER_REQRACE ? 'w':'g'
1101: ,race_ch(user.pref_race)
1102: ,user.pref_sex
1103: ,user.misc&USER_REQAGE ? 'w':'g'
1104: ,user.min_age
1105: ,user.misc&USER_REQAGE ? 'w':'g'
1106: ,user.max_age
1107: ,user.misc&USER_REQHAIR ? 'w':'g'
1108: ,hair(user.pref_hair)
1109: ,user.misc&USER_REQEYES ? 'w':'g'
1110: ,eyes(user.pref_eyes)
1111: ,user.misc&USER_REQHEIGHT ? 'w':'g'
1112: ,min
1113: ,user.misc&USER_REQHEIGHT ? 'w':'g'
1114: ,max
1115: ,user.misc&USER_REQWEIGHT ? 'w':'g'
1116: ,smm_misc&SMM_METRIC ? lptokg(user.min_weight) : user.min_weight
1117: ,user.misc&USER_REQWEIGHT ? 'w':'g'
1118: ,smm_misc&SMM_METRIC ? lptokg(user.max_weight) : user.max_weight
1119: ,user.misc&USER_REQINCOME ? 'w':'g'
1120: ,user.min_income/1000L
1121: ,user.misc&USER_REQINCOME ? 'w':'g'
1122: ,user.max_income/1000L
1123: ,user.misc&USER_REQZODIAC ? 'w':'g'
1124: ,zodiac(user.pref_zodiac));
1125:
1126: bprintf("\1r\1i%s\1n\1w\1h\r\n",user.misc&USER_PHOTO ? "PHOTO":nulstr);
1127: for(i=0;i<5;i++) {
1128: if(!user.note[i][0])
1129: break;
1130: bprintf("%15s%.50s\r\n",nulstr,user.note[i]); }
1131: }
1132:
1133: char long_user_info(user_t user)
1134: {
1135: char str[128],fname[128],path[128],ch;
1136: int i,j,k,s,u,max,match1,match2,user_match,mate_match;
1137:
1138: while(1) {
1139: checkline();
1140: main_user_info(user);
1141:
1142: CRLF;
1143: /**
1144: if(user.misc&USER_FROMSMB)
1145: bprintf("\1r\1hImported via message base from \1w%s\1r.\r\n"
1146: ,user.system);
1147: **/
1148: bprintf("\1h\1mThis user meets your profile preferences:\1w%3u%% "
1149: ,match1=basic_match(useron,user));
1150: bprintf("\1n\1gCreated: \1h%s\r\n",unixtodstr(user.created,str));
1151: bprintf("\1h\1mYou meet this user's profile preferences:\1w%3u%% "
1152: ,match2=basic_match(user,useron));
1153: bprintf("\1n\1gUpdated: \1h%s\r\n",unixtodstr(user.updated,str));
1154:
1155: if(!smm_pause)
1156: lncntr=0;
1157:
1158: CRLF;
1159: bputs("\1n\1b\1hQuestionnaires:\r\n");
1160: for(i=0;i<5;i++) {
1161: max=mate_match=user_match=0;
1162: if(!user.queans[i].name[0])
1163: continue;
1164: s=sys_quenum(user.queans[i].name);
1165: if(s==-1)
1166: continue;
1167: if(que[s]->req_age>getage(useron.birth))
1168: continue;
1169: if(match1 && match2)
1170: u=user_quenum(user.queans[i].name,useron);
1171: else
1172: u=-1;
1173: bprintf("\1h\1c%-25s ",que[s]->desc);
1174: if(u==-1) {
1175: CRLF;
1176: continue; }
1177: for(j=0;j<que[s]->total_ques;j++) {
1178: if(useron.queans[u].pref[j]&user.queans[i].self[j]) user_match+=2;
1179: if(useron.queans[u].pref[j]==user.queans[i].self[j]) user_match++;
1180: if(useron.queans[u].self[j]&user.queans[i].pref[j]) mate_match+=2;
1181: if(useron.queans[u].self[j]==user.queans[i].pref[j]) mate_match++;
1182: max+=3; }
1183: bprintf("\1n\1c%s matches your pref:\1h%3u%% "
1184: "\1n\1cYou match %s pref:\1h%3u%%\r\n"
1185: ,user.sex=='M' ? "He":"She"
1186: ,(int)(((float)user_match/max)*100.0)
1187: ,user.sex=='M' ? "his":"her"
1188: ,(int)(((float)mate_match/max)*100.0)); }
1189:
1190: bprintf("\r\n\1r\1hOverall match: \1w%u%%",total_match(useron,user));
1191: if(user.purity)
1192: bprintf(" \1r\1hPurity test: \1w%u%%",user.purity);
1193: if(user.mbtype[0])
1194: bprintf(" \1r\1hPersonality type: \1w%s",user.mbtype);
1195: CRLF;
1196:
1197: if(aborted) {
1198: aborted=0;
1199: return(0); }
1200: if(!smm_pause) {
1201: if(kbhit())
1202: return(0);
1203: return(1); }
1204: nodesync();
1205: if(lncntr>=user_rows-2)
1206: lncntr=0;
1207: CRLF;
1208: bputs("\1h\1b[\1cV\1b]iew questionnaires, ");
1209: if(user.misc&USER_PHOTO)
1210: bputs("[\1cD\1b]ownload photo, ");
1211: bputs("[\1cS\1b]end telegram, [\1cQ\1b]uit, or [Next]: \1c");
1212: strcpy(str,"VSQN\r");
1213: if(user.misc&USER_PHOTO)
1214: strcat(str,"D");
1215: if(SYSOP)
1216: strcat(str,"+");
1217: switch(getkeys(str,0)) {
1218: case '+':
1219: user.misc|=USER_PHOTO;
1220: break;
1221: case 'Q':
1222: return(0);
1223: case CR:
1224: case 'N':
1225: return(1);
1226: case 'D':
1227: if(!useron.number) {
1228: bputs("\r\n\1h\1rYou must create a profile first.\r\n");
1229: pause();
1230: break; }
1231: if(!(useron.misc&USER_PHOTO)) {
1232: bputs("\r\n\1h\1rYou cannot download photos until your photo is "
1233: "added.\r\n");
1234: pause();
1235: break; }
1236: for(i=0;user.system[i];i++)
1237: if(isalnum(user.system[i]))
1238: break;
1239: if(!user.system[i])
1240: fname[0]='~';
1241: else
1242: fname[0]=user.system[i];
1243: for(i=strlen(user.system)-1;i>0;i--)
1244: if(isalnum(user.system[i]))
1245: break;
1246: if(i<=0)
1247: fname[1]='~';
1248: else
1249: fname[1]=user.system[i];
1250: fname[2]=0;
1251: strupr(user.system);
1252: strcat(fname,base41(crc16(user.system),tmp));
1253: strcat(fname,base41(user.number,tmp));
1254: strcat(fname,".JPG");
1255: strupr(fname);
1256: sprintf(path,"PHOTO\\%s",fname);
1257: if(!fexist(path)) {
1258: bputs("\r\n\1n\1hUnpacking...");
1259: sprintf(str,"%spkunzip photo %s photo",exec_dir,fname);
1260: system(str);
1261: bputs("\r\n");
1262: if(!fexist(path)) {
1263: bputs("\r\n\1n\1h\1i\1rUnpacking failed!\1n\r\n");
1264: pause();
1265: break; } }
1266: if(com_port) {
1267: cmdstr(zmodem_send,path,path,str);
1268: ivhctl(INTCLR);
1269: ivhctl(INT29L);
1270: system(str);
1271: ivhctl(INTCLR);
1272: i=INT29L;
1273: i|=(INT29R|INT16);
1274: ivhctl(i); }
1275: else
1276: system(cmdstr(local_view,path,path,str));
1277: pause();
1278: break;
1279:
1280:
1281: case 'S':
1282: send_telegram(user);
1283: break;
1284: case 'V':
1285:
1286: if(user_level<que_level) {
1287: bputs("\r\n\1h\1rYou have insufficient access to read "
1288: "questoinnaires.\r\n");
1289: pause();
1290: break; }
1291:
1292: for(i=0;i<5;i++) {
1293: aborted=0;
1294: if(!user.queans[i].name[0])
1295: continue;
1296: s=sys_quenum(user.queans[i].name);
1297: if(s==-1)
1298: continue;
1299: if(que[s]->req_age>getage(useron.birth))
1300: continue;
1301: if(match1 && match2)
1302: u=user_quenum(user.queans[i].name,useron);
1303: else
1304: u=-1;
1305: sprintf(str,"\r\nDo you wish to view the \1w%s\1b questionnaire"
1306: ,que[s]->desc);
1307: if(!yesno(str))
1308: continue;
1309: if(!cdt_warning(que_cdt))
1310: continue;
1311: adjust_cdt(que_cdt);
1312: for(j=0;j<que[s]->total_ques && !aborted;) {
1313: cls();
1314: bprintf("\1n\1m\1hQuestionnaire: \1y%-25s \1mQuestion: "
1315: "\1y%d \1mof \1y%d \1h\1b(Ctrl-C to Abort)\r\n\r\n"
1316: ,que[s]->desc,j+1,que[s]->total_ques);
1317: bprintf("\1w\1h%s\r\n\r\n",que[s]->que[j].txt);
1318: for(k=0;k<que[s]->que[j].answers;k++)
1319: bprintf("\1h\1b%c\1w) \1g%s\r\n",'A'+k
1320: ,que[s]->que[j].ans[k]);
1321: bits2str(user.queans[i].self[j],str);
1322: bprintf("\1n\1g\r\n%25s: \1h%-16s "
1323: ,user.name,str);
1324: bits2str(user.queans[i].pref[j],str);
1325: bprintf("\1n\1g %15s: \1h%s","Preferred mate",str);
1326: if(u!=-1) {
1327: bits2str(useron.queans[u].pref[j],str);
1328: bprintf("\1n\1g\r\n%25s: \1h%-16s "
1329: ,"Your preferred mate",str);
1330: bits2str(useron.queans[u].self[j],str);
1331: bprintf("\1n\1g %15s: \1h%s","You",str); }
1332: CRLF;
1333: if(!aborted) {
1334: lncntr=0;
1335: bputs("\r\n\1h\1b[\1cP\1b]revious, [\1cQ\1b]uit, "
1336: "or [Next]: \1c");
1337: ch=getkeys("PQN\r",0);
1338: if(ch=='P') {
1339: if(j) j--;
1340: continue; }
1341: if(ch=='Q')
1342: break;
1343: j++; } } }
1344: break;
1345:
1346: } }
1347: return(0);
1348: }
1349:
1350:
1351: /* Returns 0 if aborted, 1 if continue, negative if previous */
1352: int short_user_info(user_t user)
1353: {
1354: char str[128],height[64],ch;
1355: int i,match;
1356: int records;
1357: ulong name_crc;
1358: static char name[26],lastname[26],highmatch;
1359: static long topixb,topdab,lastixb,lastdab;
1360: static int count;
1361:
1362: if(!lncntr && smm_pause) {
1363: topdab=ftell(stream)-sizeof(user_t);
1364: topixb=ftell(index)-sizeof(ixb_t);
1365: if(!topdab)
1366: lastdab=lastixb=0;
1367: count=0;
1368: printfile("LIST_HDR.ASC");
1369: strcpy(lastname,name);
1370: name[0]=highmatch=0; }
1371: if(user.number) {
1372: match=total_match(useron,user);
1373: if(!match) str[0]=0;
1374: else if(match>=90) sprintf(str,"\1w%u%%",match);
1375: else if(match>=80) sprintf(str,"\1c%u%%",match);
1376: else if(match>=70) sprintf(str,"\1y%u%%",match);
1377: else if(match>=60) sprintf(str,"\1g%u%%",match);
1378: else if(match>=50) sprintf(str,"\1m%u%%",match);
1379: else if(match>=40) sprintf(str,"\1r%u%%",match);
1380: else if(match>=30) sprintf(str,"\1b%u%%",match);
1381: else if(match>=20) sprintf(str,"\1n\1g%u%%",match);
1382: else if(match>=10) sprintf(str,"\1n\1c%u%%",match);
1383: else sprintf(str,"\1n%u%%",match);
1384: if(smm_misc&SMM_METRIC)
1385: sprintf(height," %-4u",intocm(user.height));
1386: else
1387: sprintf(height,"%2u'%-2u",user.height/12,user.height%12);
1388: bprintf("\1n\1h%c\1n\1g%c\1h\1c%c\1b%3u \1g%3s \1m%3s\1r%s \1y%-3u "
1389: "\1n\1g%-25.25s\1r\1h\1i%c\1n\1h%-25.25s%s\r\n"
1390: ,user.sex==user.pref_sex ? 'G':user.sex=='*' ? 'B'
1391: : marital_ch(user.marital)
1392: ,race_ch(user.race)
1393: ,user.sex
1394: ,getage(user.birth)
1395: ,hair(user.hair)
1396: ,eyes(user.eyes)
1397: ,height
1398: ,smm_misc&SMM_METRIC ? lptokg(user.weight) : user.weight
1399: ,user.location
1400: ,user.misc&USER_PHOTO ? '+':SP
1401: ,user.name
1402: ,str
1403: );
1404: if(match &&
1405: (!name[0] || !stricmp(name,lastname)
1406: || (stricmp(user.name,lastname) && match>highmatch))) {
1407: highmatch=match;
1408: sprintf(name,"%.25s",user.name);
1409: strupr(name); }
1410: }
1411:
1412: if(lncntr>=user_rows-2 || !user.number) {
1413: lncntr=0;
1414: bputs(PrevReadSendQuitOrMore);
1415: ch=getkey(K_UPPER);
1416: if(ch=='Q') {
1417: cls();
1418: aborted=1; }
1419: else if(ch=='P') {
1420: cls();
1421: records=((ftell(stream)-topdab)/sizeof(user_t));
1422: fseek(stream,lastdab,SEEK_SET);
1423: fseek(index,lastixb,SEEK_SET);
1424: lastdab-=(records)*sizeof(user_t);
1425: lastixb-=(records)*sizeof(ixb_t);
1426: if(lastdab<0) lastdab=0;
1427: if(lastixb<0) lastixb=0;
1428: return(-count); }
1429: else if(ch=='R' || ch=='G' || ch=='S') {
1430: bprintf("\1n\r\1>\1y\1hUser name: ");
1431: if(getstr(name,25,K_NOCRLF|K_LINE|K_EDIT|K_AUTODEL|K_UPPER)) {
1432: truncsp(name);
1433: name_crc=crc32(name);
1434: cls();
1435: rewind(index);
1436: while(!feof(index)) {
1437: if(!fread(&ixb,sizeof(ixb_t),1,index))
1438: break;
1439: if(!ixb.number) /* DELETED */
1440: continue;
1441: if(ixb.name!=name_crc)
1442: continue;
1443: fseek(stream
1444: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
1445: *sizeof(user_t),SEEK_SET);
1446: if(!fread(&user,sizeof(user_t),1,stream))
1447: continue;
1448: if(ch=='S' && send_telegram(user))
1449: break;
1450: if(ch!='S' && !long_user_info(user))
1451: break; } }
1452: fseek(stream,topdab,SEEK_SET);
1453: fseek(index,topixb,SEEK_SET);
1454: cls();
1455: return(-1); }
1456: else {
1457: lastixb=topixb;
1458: lastdab=topdab;
1459: cls(); } }
1460:
1461: count++;
1462: if(aborted)
1463: return(0);
1464: return(1);
1465: }
1466:
1467:
1468: int get_your_det(user_t *user)
1469: {
1470: char str[128],*p,*hdr;
1471: int i;
1472:
1473: while(1) {
1474: checkline();
1475: cls();
1476: bputs("\1h\0014 Your Detailed Personal Information \1n \1h\1b"
1477: "(Ctrl-C to Abort)\r\n\r\n");
1478:
1479: nodesync();
1480: bputs("\1h\1bPlease enter your name or alias: ");
1481: strcpy(str,user->name);
1482: if(!getstr(str,25,K_LINE|K_EDIT|K_AUTODEL|K_UPRLWR))
1483: return(0);
1484: truncsp(str);
1485: if(trash(str)) {
1486: bprintf("\r\n\1h\1rSorry, you can't use that name.\r\n\r\n\1p");
1487: continue; }
1488: strcpy(user->name,str);
1489:
1490: CRLF;
1491: nodesync();
1492: bprintf("\1h\1gPlease enter your height in %s: "
1493: ,smm_misc&SMM_METRIC ? "centimeters" : "feet'inches (example: 5'7)");
1494: if(user->height) {
1495: if(smm_misc&SMM_METRIC)
1496: sprintf(str,"%u",intocm(user->height));
1497: else
1498: sprintf(str,"%u'%u",user->height/12,user->height%12); }
1499: else
1500: str[0]=0;
1501: if(!getstr(str,4,K_LINE|K_EDIT|K_AUTODEL))
1502: return(0);
1503: if(smm_misc&SMM_METRIC)
1504: user->height=cmtoin(atoi(str));
1505: else {
1506: user->height=atoi(str)*12;
1507: p=strchr(str,'\'');
1508: if(p) user->height+=atoi(p+1); }
1509:
1510: CRLF;
1511: nodesync();
1512: bprintf("\1h\1mPlease enter your weight (in %s): "
1513: ,smm_misc&SMM_METRIC ? "kilograms":"pounds");
1514: if(user->weight)
1515: sprintf(str,"%u"
1516: ,smm_misc&SMM_METRIC ? lptokg(user->weight) : user->weight);
1517: else
1518: str[0]=0;
1519: if(!getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL|K_LINE))
1520: return(0);
1521: if(smm_misc&SMM_METRIC)
1522: user->weight=kgtolp(atoi(str));
1523: else
1524: user->weight=atoi(str);
1525:
1526: CRLF;
1527: nodesync();
1528: bputs("\1h\1rPlease enter your annual income in dollars (ENTER=undisclosed): ");
1529: if(user->income && user->income!=0xffffffff)
1530: sprintf(str,"%luK",user->income/1000);
1531: else
1532: str[0]=0;
1533: getstr(str,6,K_UPPER|K_EDIT|K_AUTODEL|K_LINE);
1534: if(aborted)
1535: return(0);
1536: if(strchr(str,'K'))
1537: user->income=atol(str)*1000L;
1538: else if(str[0]==0)
1539: user->income=0xffffffffUL;
1540: else
1541: user->income=atol(str);
1542:
1543: CRLF;
1544: nodesync();
1545: bputs("\1h\1cPlease enter your location (city, state): ");
1546: strcpy(str,user->location);
1547: if(!getstr(str,30,K_LINE|K_EDIT|K_AUTODEL|K_UPRLWR))
1548: return(0);
1549: truncsp(str);
1550: if(trash(str)) {
1551: bprintf("\r\n\1r\1hSorry, you can't use that location.\r\n\r\n\1p");
1552: continue; }
1553: strcpy(user->location,str);
1554:
1555:
1556: CRLF;
1557: nodesync();
1558: bputs("\1h\1gPlease enter your zip/postal code: ");
1559: if(!getstr(user->zipcode,10,K_LINE|K_EDIT|K_AUTODEL))
1560: return(0);
1561:
1562: CRLF;
1563: nodesync();
1564: for(i=0;i<5;i++) {
1565: bprintf("\1n\1gPersonal text - Line %u of 5: ",i+1);
1566: if(wordwrap[0])
1567: user->note[i][0]=0;
1568: strcpy(str,user->note[i]);
1569: if(!getstr(str,50,i==4 ? K_LINE|K_EDIT:K_LINE|K_EDIT|K_WRAP))
1570: break;
1571: if(trash(str)) {
1572: bprintf("\r\n\1r\1hSorry, you can't use that text.\r\n\r\n");
1573: i--;
1574: continue; }
1575: strcpy(user->note[i],str); }
1576: while(i++<5)
1577: user->note[i][0]=0;
1578: aborted=0;
1579: nodesync();
1580: if(yesno("\r\nIs the above information correct"))
1581: break; }
1582: return(1);
1583: }
1584:
1585: int get_pref_det(user_t *user)
1586: {
1587: char str[128],*p,*hdr;
1588: int i;
1589:
1590: while(1) {
1591: checkline();
1592: cls();
1593: bputs("\1h\0014 Detailed Information on Your Preferred Mate \1n "
1594: "\1h\1b(Ctrl-C to Abort)\r\n\r\n");
1595:
1596: nodesync();
1597: bputs("\1n\1cPlease enter the minimum age of your preferred mate: \1h");
1598: if(user->min_age)
1599: sprintf(str,"%u",user->min_age);
1600: else
1601: str[0]=0;
1602: getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL);
1603: if(aborted)
1604: return(0);
1605: user->min_age=atoi(str);
1606:
1607: nodesync();
1608: bputs("\1h\1cPlease enter the maximum age of your preferred mate: \1h");
1609: if(user->max_age)
1610: sprintf(str,"%u",user->max_age);
1611: else
1612: str[0]=0;
1613: getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL);
1614: if(aborted)
1615: return(0);
1616: user->max_age=atoi(str);
1617: if(user->min_age) {
1618: strcpy(str,"Do you require your mate's age fall within this range");
1619: if(user->misc&USER_REQAGE)
1620: i=yesno(str);
1621: else
1622: i=!noyes(str);
1623: if(i)
1624: user->misc|=USER_REQAGE;
1625: else
1626: user->misc&=~USER_REQAGE; }
1627: else
1628: user->misc&=~USER_REQAGE;
1629: if(aborted)
1630: return(0);
1631:
1632: CRLF;
1633: nodesync();
1634: bprintf("\1n\1gPlease enter the minimum height of your preferred mate "
1635: "in %s: \1w\1h",smm_misc&SMM_METRIC ? "centimeters":"feet'inches");
1636: if(user->min_height) {
1637: if(smm_misc&SMM_METRIC)
1638: sprintf(str,"%u",intocm(user->min_height));
1639: else
1640: sprintf(str,"%u'%u",user->min_height/12,user->min_height%12); }
1641: else
1642: str[0]=0;
1643: getstr(str,4,K_EDIT|K_AUTODEL);
1644: if(aborted)
1645: return(0);
1646: if(smm_misc&SMM_METRIC)
1647: user->min_height=cmtoin(atoi(str));
1648: else {
1649: user->min_height=atoi(str)*12;
1650: p=strchr(str,'\'');
1651: if(p) user->min_height+=atoi(p+1); }
1652: nodesync();
1653: bprintf("\1h\1gPlease enter the maximum height of your preferred mate "
1654: "in %s: \1w",smm_misc&SMM_METRIC ? "centimeters":"feet'inches");
1655: if(user->max_height) {
1656: if(smm_misc&SMM_METRIC)
1657: sprintf(str,"%u",intocm(user->max_height));
1658: else
1659: sprintf(str,"%u'%u",user->max_height/12,user->max_height%12); }
1660: else
1661: str[0]=0;
1662: getstr(str,4,K_EDIT|K_AUTODEL);
1663: if(aborted)
1664: return(0);
1665: if(smm_misc&SMM_METRIC)
1666: user->max_height=cmtoin(atoi(str));
1667: else {
1668: user->max_height=atoi(str)*12;
1669: p=strchr(str,'\'');
1670: if(p) user->max_height+=atoi(p+1); }
1671: strcpy(str,"Do you require your mate's height fall within this range");
1672: if(user->misc&USER_REQHEIGHT)
1673: i=yesno(str);
1674: else
1675: i=!noyes(str);
1676: if(i)
1677: user->misc|=USER_REQHEIGHT;
1678: else
1679: user->misc&=~USER_REQHEIGHT;
1680: if(aborted)
1681: return(0);
1682:
1683:
1684: CRLF;
1685: nodesync();
1686: bprintf("\1n\1mPlease enter the minimum weight of your preferred mate in %s:"
1687: " \1w\1h",smm_misc&SMM_METRIC ? "kilograms":"pounds");
1688: if(user->min_weight) {
1689: if(smm_misc&SMM_METRIC)
1690: sprintf(str,"%u",lptokg(user->min_weight));
1691: else
1692: sprintf(str,"%u",user->min_weight); }
1693: else
1694: str[0]=0;
1695: getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL);
1696: if(aborted)
1697: return(0);
1698: if(smm_misc&SMM_METRIC)
1699: user->min_weight=kgtolp(atoi(str));
1700: else
1701: user->min_weight=atoi(str);
1702:
1703: nodesync();
1704: bprintf("\1h\1mPlease enter the maximum weight of your preferred mate in %s:"
1705: " \1w",smm_misc&SMM_METRIC ? "kilograms":"pounds");
1706: if(user->max_weight) {
1707: if(smm_misc&SMM_METRIC)
1708: sprintf(str,"%u",lptokg(user->max_weight));
1709: else
1710: sprintf(str,"%u",user->max_weight); }
1711: else
1712: str[0]=0;
1713: getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL);
1714: if(aborted)
1715: return(0);
1716: if(smm_misc&SMM_METRIC)
1717: user->max_weight=kgtolp(atoi(str));
1718: else
1719: user->max_weight=atoi(str);
1720: if(user->max_weight) {
1721: strcpy(str,"Do you require your mate's weight fall within this range");
1722: if(user->misc&USER_REQWEIGHT)
1723: i=yesno(str);
1724: else
1725: i=!noyes(str);
1726: if(i)
1727: user->misc|=USER_REQWEIGHT;
1728: else
1729: user->misc&=~USER_REQWEIGHT; }
1730: else
1731: user->misc&=~USER_REQWEIGHT;
1732: if(aborted)
1733: return(0);
1734:
1735:
1736: CRLF;
1737: nodesync();
1738: bputs("\1h\1cPlease enter the lowest zip/postal code of your preferred "
1739: "mate: \1w");
1740: getstr(user->min_zipcode,10,K_EDIT|K_AUTODEL|K_UPPER);
1741: if(aborted)
1742: return(0);
1743: bputs("\1h\1bPlease enter the highest zip/postal code of your preferred "
1744: "mate: \1w");
1745: getstr(user->max_zipcode,10,K_EDIT|K_AUTODEL|K_UPPER);
1746: if(aborted)
1747: return(0);
1748: strcpy(str,"Do you require your mate's zip/postal code fall within this range");
1749: if(user->misc&USER_REQZIP)
1750: i=yesno(str);
1751: else
1752: i=!noyes(str);
1753: if(i)
1754: user->misc|=USER_REQZIP;
1755: else
1756: user->misc&=~USER_REQZIP;
1757: if(aborted)
1758: return(0);
1759:
1760:
1761: CRLF;
1762: nodesync();
1763: bputs("\1h\1gPlease enter the minimum annual income of your "
1764: "mate in dollars: \1w");
1765: if(user->min_income)
1766: sprintf(str,"%lu",user->min_income);
1767: else
1768: str[0]=0;
1769: getstr(str,6,K_NUMBER|K_EDIT|K_AUTODEL);
1770: if(aborted) return(0);
1771: user->min_income=atol(str);
1772:
1773: nodesync();
1774: bputs("\1h\1yPlease enter the maximum annual income of your "
1775: "mate in dollars: \1w");
1776: if(user->max_income)
1777: sprintf(str,"%lu",user->max_income);
1778: else
1779: str[0]=0;
1780: getstr(str,6,K_NUMBER|K_EDIT|K_AUTODEL);
1781: if(aborted) return(0);
1782: user->max_income=atol(str);
1783: if(user->min_income) {
1784: strcpy(str,"Do you require that your mate's income fall within this range");
1785: if(user->misc&USER_REQINCOME)
1786: i=yesno(str);
1787: else
1788: i=!noyes(str);
1789: if(i)
1790: user->misc|=USER_REQINCOME;
1791: else
1792: user->misc&=~USER_REQINCOME; }
1793: else
1794: user->misc&=~USER_REQINCOME;
1795: if(aborted)
1796: return(0);
1797:
1798:
1799: nodesync();
1800: if(yesno("\r\nIs the above information correct"))
1801: break; }
1802: return(1);
1803: }
1804:
1805: int get_your_multi(user_t *user)
1806: {
1807: char str[128],*hdr,*p;
1808:
1809: while(1) {
1810: checkline();
1811: hdr="\1n\1l\1h\0014 Your Profile \1n \1h\1b(Ctrl-C to Abort)\r\n\r\n";
1812: bputs(hdr);
1813: bputs("\1n\1h\1cYour Marital Status:\r\n\r\n");
1814: mnemonics("~A) Single\r\n~B) Married\r\n~C) Divorced\r\n~D) Widowed\r\n"
1815: "~E) Other\r\n");
1816: nodesync();
1817: bputs("\r\n\1y\1hWhich: \1w");
1818: uchar2ans(user->marital,str);
1819: if(!getstr(str,1,K_ALPHA|K_LINE|K_EDIT|K_AUTODEL|K_UPPER))
1820: return(0);
1821: if(str[0]<='E')
1822: break; }
1823: user->marital=ans2uchar(str);
1824:
1825: while(1) {
1826: checkline();
1827: bputs(hdr);
1828: bputs("\1n\1h\1cYour Race:\r\n\r\n");
1829: mnemonics("~A) White\r\n~B) Black\r\n~C) Hispanic\r\n~D) Asian\r\n"
1830: "~E) American Indian\r\n~F) Middle Eastern\r\n~G) Other\r\n");
1831: nodesync();
1832: bputs("\r\n\1y\1hWhich: \1w");
1833: uchar2ans(user->race,str);
1834: if(!getstr(str,1,K_ALPHA|K_LINE|K_EDIT|K_AUTODEL|K_UPPER))
1835: return(0);
1836: if(str[0]<='G')
1837: break; }
1838: user->race=ans2uchar(str);
1839:
1840: while(1) {
1841: checkline();
1842: bputs(hdr);
1843: bputs("\1n\1h\1cYour Hair Color:\r\n\r\n");
1844: mnemonics("~A) Blonde\r\n~B) Brown\r\n~C) Red\r\n~D) Black\r\n"
1845: "~E) Grey\r\n~F) Other\r\n");
1846: nodesync();
1847: bputs("\r\n\1y\1hWhich: \1w");
1848: uchar2ans(user->hair,str);
1849: if(!getstr(str,1,K_ALPHA|K_LINE|K_EDIT|K_AUTODEL|K_UPPER))
1850: return(0);
1851: if(str[0]<='F')
1852: break; }
1853: user->hair=ans2uchar(str);
1854:
1855: while(1) {
1856: checkline();
1857: bputs(hdr);
1858: bputs("\1n\1h\1cYour Eye Color:\r\n\r\n");
1859: mnemonics("~A) Blue\r\n~B) Green\r\n~C) Hazel\r\n~D) Brown\r\n"
1860: "~E) Other\r\n");
1861: nodesync();
1862: bputs("\r\n\1y\1hWhich: \1w");
1863: uchar2ans(user->eyes,str);
1864: if(!getstr(str,1,K_ALPHA|K_LINE|K_EDIT|K_AUTODEL|K_UPPER))
1865: return(0);
1866: if(str[0]<='E')
1867: break; }
1868: user->eyes=ans2uchar(str);
1869: return(1);
1870: }
1871:
1872: int get_pref_multi(user_t *user)
1873: {
1874: char str[128],*hdr,*p;
1875: int i;
1876:
1877: while(1) {
1878: checkline();
1879: hdr="\1n\1l\1h\0014 Profile of Your Preferred Mate \1n \1h\1b"
1880: "(Ctrl-C to Abort)\r\n\r\n";
1881: bputs(hdr);
1882: bputs("\1n\1h\1cSex of Your Preferred (Intimate/Romantic) Mate:\r\n\r\n");
1883: mnemonics("~M) Male\r\n~F) Female\r\n~*) Either\r\n");
1884: nodesync();
1885: bputs("\r\n\1y\1hWhich: ");
1886: str[0]=user->pref_sex;
1887: str[1]=0;
1888: if(!getstr(str,1,K_UPPER|K_EDIT|K_AUTODEL|K_LINE))
1889: break;
1890: if(user->sex==str[0] && noyes("\r\nYou are homosexual"))
1891: continue;
1892: if(str[0]=='M' || str[0]=='F' || str[0]=='*')
1893: break; }
1894: user->pref_sex=str[0];
1895: if(aborted) return(0);
1896:
1897: strcpy(str,"\r\nAre you seeking an any-sex (non-romantic) friendship");
1898: if(user->misc&USER_FRIEND)
1899: i=yesno(str);
1900: else
1901: i=!noyes(str);
1902: if(i)
1903: user->misc|=USER_FRIEND;
1904: else
1905: user->misc&=~USER_FRIEND;
1906:
1907: bputs(hdr);
1908: bputs("\1n\1h\1cMarital Status of Your Preferred Mate:\r\n\r\n");
1909: mnemonics("~A) Single\r\n~B) Married\r\n~C) Divorced\r\n~D) Widowed\r\n"
1910: "~E) Other\r\n~*) Any of the above\r\n");
1911: nodesync();
1912: bputs("\r\n\1y\1hPlease enter up to 4 answers: ");
1913: uchar2ans(user->pref_marital,str);
1914: if(!getstr(str,4,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
1915: return(0);
1916: user->pref_marital=ans2uchar(str);
1917: if(user->pref_marital!=0xff) {
1918: strcpy(str,"\r\nDo you require your mate have the martial status you "
1919: "indicated");
1920: if(user->misc&USER_REQMARITAL)
1921: i=yesno(str);
1922: else
1923: i=!noyes(str);
1924: if(i)
1925: user->misc|=USER_REQMARITAL;
1926: else
1927: user->misc&=~USER_REQMARITAL; }
1928: else
1929: user->misc&=~USER_REQMARITAL;
1930: if(aborted) return(0);
1931:
1932: bputs(hdr);
1933: bputs("\1n\1h\1cRace of Your Preferred Mate:\r\n\r\n");
1934: mnemonics("~A) White\r\n~B) Black\r\n~C) Hispanic\r\n~D) Asian\r\n"
1935: "~E) American Indian\r\n~F) Middle Eastern\r\n~G) Other\r\n"
1936: "~*) Any of the above\r\n");
1937: nodesync();
1938: bputs("\r\n\1y\1hPlease enter up to 6 answers: ");
1939: uchar2ans(user->pref_race,str);
1940: if(!getstr(str,6,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
1941: return(0);
1942: user->pref_race=ans2uchar(str);
1943: if(user->pref_race!=0xff) {
1944: strcpy(str,"\r\nDo you require your mate be of the race"
1945: " you indicated");
1946: if(user->misc&USER_REQRACE)
1947: i=yesno(str);
1948: else
1949: i=!noyes(str);
1950: if(i)
1951: user->misc|=USER_REQRACE;
1952: else
1953: user->misc&=~USER_REQRACE; }
1954: else
1955: user->misc&=~USER_REQRACE;
1956: if(aborted) return(0);
1957:
1958: bputs(hdr);
1959: bputs("\1n\1h\1cHair Color of Your Preferred Mate:\r\n\r\n");
1960: mnemonics("~A) Blonde\r\n~B) Brown\r\n~C) Red\r\n~D) Black\r\n"
1961: "~E) Grey\r\n~F) Other\r\n~*) Any of the Above\r\n");
1962: nodesync();
1963: bputs("\r\n\1y\1hPlease enter up to 5 answers: ");
1964: uchar2ans(user->pref_hair,str);
1965: if(!getstr(str,5,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
1966: return(0);
1967: user->pref_hair=ans2uchar(str);
1968: if(user->pref_hair!=0xff) {
1969: strcpy(str,"\r\nDo you require your mate have the hair color"
1970: " you indicated");
1971: if(user->misc&USER_REQHAIR)
1972: i=yesno(str);
1973: else
1974: i=!noyes(str);
1975: if(i)
1976: user->misc|=USER_REQHAIR;
1977: else
1978: user->misc&=~USER_REQHAIR; }
1979: else
1980: user->misc&=~USER_REQHAIR;
1981: if(aborted) return(0);
1982:
1983:
1984: bputs(hdr);
1985: bputs("\1n\1h\1cEye Color of Your Preferred Mate:\r\n\r\n");
1986: mnemonics("~A) Blue\r\n~B) Green\r\n~C) Hazel\r\n~D) Brown\r\n"
1987: "~E) Other\r\n~*) Any of the above\r\n");
1988: nodesync();
1989: bputs("\r\n\1y\1hPlease enter up to 4 answers: ");
1990: uchar2ans(user->pref_eyes,str);
1991: if(!getstr(str,4,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
1992: return(0);
1993: user->pref_eyes=ans2uchar(str);
1994: if(user->pref_eyes!=0xff) {
1995: strcpy(str,"\r\nDo you require your mate have the eye color"
1996: " you indicated");
1997: if(user->misc&USER_REQEYES)
1998: i=yesno(str);
1999: else
2000: i=!noyes(str);
2001: if(i)
2002: user->misc|=USER_REQEYES;
2003: else
2004: user->misc&=~USER_REQEYES; }
2005: else
2006: user->misc&=~USER_REQEYES;
2007: if(aborted) return(0);
2008:
2009: bputs(hdr);
2010: bputs("\1n\1h\1cZodiac Sign of Your Preferred Mate:\r\n\r\n");
2011: mnemonics("~A) Aries\r\n~B) Taurus\r\n~C) Gemini\r\n~D) Cancer\r\n"
2012: "~E) Leo\r\n~F) Virgo\r\n~G) Libra\r\n~H) Scorpio\r\n");
2013: mnemonics("~I) Sagittarius\r\n~J) Capricorn\r\n~K) Aquarius\r\n"
2014: "~L) Pisces\r\n~*) Any of the above\r\n");
2015: nodesync();
2016: bputs("\r\n\1y\1hPlease enter up to 11 answers: ");
2017: bits2ans(user->pref_zodiac,str);
2018: if(!getstr(str,11,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
2019: return(0);
2020: user->pref_zodiac=ans2bits(str);
2021: if(user->pref_zodiac!=0xffff) {
2022: strcpy(str,"\r\nDo you require your mate have the zodiac sign"
2023: " you indicated");
2024: if(user->misc&USER_REQZODIAC)
2025: i=yesno(str);
2026: else
2027: i=!noyes(str);
2028: if(i)
2029: user->misc|=USER_REQZODIAC;
2030: else
2031: user->misc&=~USER_REQZODIAC; }
2032: else
2033: user->misc&=~USER_REQZODIAC;
2034: if(aborted) return(0);
2035:
2036: return(1);
2037: }
2038:
2039: void mbtype_desc(char *mbtype)
2040: {
2041: char str[128],type[128];
2042:
2043: while(1) {
2044: checkline();
2045: cls();
2046: printfile("MB-TYPE.ASC");
2047: nodesync();
2048: bprintf("\r\n\1y\1hYour Type: \1w%s\r\n",mbtype);
2049: bputs("\1y\1hLetter or Type to define: ");
2050: memset(type,0,5);
2051: if(!getstr(type,4,K_ALPHA|K_UPPER|K_LINE))
2052: break;
2053: sprintf(str,"MB-%s.ASC",type);
2054: if(!fexist(str)) {
2055: bputs("\r\nInvalid Letter or Type!\r\n\r\n");
2056: pause();
2057: continue; }
2058: cls();
2059: printfile(str);
2060: if(lncntr && !aborted)
2061: pause(); }
2062: }
2063:
2064:
2065: int get_mbtype(user_t *user)
2066: {
2067: char str[256];
2068: int file,i=0,e=0,n=0,s=0,f=0,t=0,p=0,j=0,q=0,ch;
2069: FILE *stream;
2070:
2071: aborted=0;
2072: cls();
2073: printfile("MB-INTRO.ASC");
2074: if(aborted)
2075: return(0);
2076: bputs("\1n\1hYour answers will be kept secret.\r\n\r\n"
2077: "Only your personality type will be visible to other users.\r\n\r\n");
2078: nodesync();
2079: if(!yesno("Continue with test"))
2080: return(0);
2081:
2082: if((file=nopen("MB-TYPE.QUE",O_RDONLY))==-1 ||
2083: (stream=fdopen(file,"r"))==NULL) {
2084: bputs("\7\r\i\hCan't open MBTYPE.QUE\r\n\1p");
2085: return(0); }
2086: while(!feof(stream)) {
2087: if(!fgets(str,200,stream))
2088: break;
2089: str[57]=0;
2090: truncsp(str);
2091: if(!str[0])
2092: break;
2093: cls();
2094: nodesync();
2095: bprintf("\1y\1hMyers-Briggs Personality Test \1bQuestion #\1w%u "
2096: "\1b(Ctrl-C to Abort)\r\n"
2097: "\r\n%s:\r\n\r\n"
2098: "[\1wA\1b] %.44s\r\n"
2099: "[\1wB\1b] %.44s\r\n"
2100: "[\1wC\1b] cannot decide\r\n\r\n"
2101: "Which: \1w"
2102: ,q+1,str,str+58,str+102);
2103: ch=getkeys("ABC",0);
2104: if(aborted) {
2105: fclose(stream);
2106: return(0); }
2107: if(ch=='C') {
2108: q++;
2109: continue; }
2110:
2111: if(ch=='A')
2112: ch=str[146];
2113: else
2114: ch=str[147];
2115:
2116: switch(ch) {
2117: case 'E':
2118: e++;
2119: break;
2120: case 'I':
2121: i++;
2122: break;
2123: case 'S':
2124: s++;
2125: break;
2126: case 'N':
2127: n++;
2128: break;
2129: case 'T':
2130: t++;
2131: break;
2132: case 'F':
2133: f++;
2134: break;
2135: case 'J':
2136: j++;
2137: break;
2138: case 'P':
2139: p++;
2140: break; }
2141: q++; }
2142:
2143: fclose(stream);
2144:
2145: if(i>e)
2146: user->mbtype[0]='I';
2147: else if(i==e)
2148: user->mbtype[0]='*';
2149: else
2150: user->mbtype[0]='E';
2151:
2152: if(s>n)
2153: user->mbtype[1]='S';
2154: else if(s==n)
2155: user->mbtype[1]='*';
2156: else
2157: user->mbtype[1]='N';
2158:
2159: if(t>f)
2160: user->mbtype[2]='T';
2161: else if(t==f)
2162: user->mbtype[2]='*';
2163: else
2164: user->mbtype[2]='F';
2165:
2166: if(p>j)
2167: user->mbtype[3]='P';
2168: else if(p==j)
2169: user->mbtype[3]='*';
2170: else
2171: user->mbtype[3]='J';
2172:
2173: bprintf("\1l\1y\1hYour Myers-Briggs Personality Type is \1w%s\r\n\r\n"
2174: ,user->mbtype);
2175:
2176: if(yesno("Would you like to see the personality type descriptions"))
2177: mbtype_desc(user->mbtype);
2178: return(1);
2179: }
2180:
2181:
2182: int get_purity(user_t *user)
2183: {
2184: char str[128];
2185: int file,no_ans=0,pos_ans=0;
2186: FILE *stream;
2187:
2188: aborted=0;
2189: if(!fexist("PURITY.QUE") || purity_age>getage(user->birth))
2190: return(0);
2191: cls();
2192: printfile("PURITY.ASC");
2193: if(aborted)
2194: return(0);
2195: bputs("\1n\1hYour answers will be kept secret.\r\n\r\n"
2196: "Only your purity score will be visible to other users.\r\n\r\n");
2197: nodesync();
2198: if(!yesno("Continue with test"))
2199: return(0);
2200: if((file=nopen("PURITY.QUE",O_RDONLY))==-1 ||
2201: (stream=fdopen(file,"r"))==NULL) {
2202: bputs("\7\r\i\hCan't open PURITY.QUE\r\n\1p");
2203: return(0); }
2204: while(!feof(stream)) {
2205: if(!fgets(str,81,stream))
2206: break;
2207: truncsp(str);
2208: cls();
2209: if(str[0]=='*') {
2210: printfile(str+1);
2211: if(lncntr && !aborted)
2212: pause();
2213: if(aborted)
2214: break;
2215: continue; }
2216: nodesync();
2217: bprintf("\1y\1hPurity Test \1bQuestion #\1w%u \1b(Ctrl-C to Abort)\r\n"
2218: "\r\nHave you ever:\r\n\r\n"
2219: ,++pos_ans);
2220: if(noyes(str))
2221: no_ans++;
2222: if(aborted)
2223: break; }
2224:
2225: fclose(stream);
2226: if(aborted)
2227: return(0);
2228:
2229: user->purity=((float)no_ans/pos_ans)*100.0;
2230: bprintf("\1l\1y\1hCongratulations, you are \1w%u%%\1y pure!\r\n\r\n"
2231: ,user->purity);
2232: pause();
2233: return(1);
2234: }
2235:
2236: int get_que(int i, user_t *inuser)
2237: {
2238: char str[128];
2239: int j,k,x,y,u;
2240: user_t user=*inuser;
2241:
2242: if(que[i]->req_age>getage(inuser->birth))
2243: return(0);
2244: for(j=0;j<que[i]->total_ques && !aborted;j++) {
2245:
2246: u=user_quenum(que[i]->name,user);
2247: if(u==-1) { /* not already answered */
2248: for(u=0;u<5;u++) /* search for unused questionnaire slot */
2249: if(sys_quenum(user.queans[u].name)==-1)
2250: break;
2251: if(u==5) { /* All questionnaire slots used!?? */
2252: bputs("\r\n\7Questionnaire error, inform sysop!\r\n");
2253: pause();
2254: return(0); } }
2255: strcpy(user.queans[u].name,que[i]->name);
2256: cls();
2257: bprintf("\1n\1m\1hQuestionnaire: \1y%-25s \1mQuestion: "
2258: "\1y%d \1mof \1y%d \1h\1b(Ctrl-C to Abort)\r\n\r\n"
2259: ,que[i]->desc,j+1,que[i]->total_ques);
2260: bprintf("\1w\1h%s\r\n\r\n",que[i]->que[j].txt);
2261: for(k=0;k<que[i]->que[j].answers;k++)
2262: bprintf("\1h\1b%c\1w) \1g%s\r\n",'A'+k,que[i]->que[j].ans[k]);
2263: nodesync();
2264: bprintf("\1n\1g\r\nChoose %s%d answer%s to describe "
2265: "\1hyourself\1n\1g%s: "
2266: ,que[i]->que[j].allowed > 1 ? "up to ":""
2267: ,que[i]->que[j].allowed,que[i]->que[j].allowed > 1 ? "s":""
2268: ,j ? " or \1h-\1n\1g to go back" : "");
2269: bits2ans(user.queans[u].self[j],str);
2270: getstr(str,que[i]->que[j].allowed,K_UPPER|K_LINE|K_EDIT|K_AUTODEL);
2271: if(aborted)
2272: return(0);
2273: truncsp(str);
2274: if(!str[0]) {
2275: j--;
2276: continue; }
2277: if(str[0]=='-') {
2278: if(j) j-=2;
2279: else j--;
2280: continue; }
2281: y=strlen(str);
2282: for(x=0;x<y;x++)
2283: if(!isalpha(str[x]) || str[x]-'A'>que[i]->que[j].answers-1)
2284: break;
2285: if(x<y) {
2286: j--;
2287: continue; }
2288: user.queans[u].self[j]=ans2bits(str);
2289: nodesync();
2290: bprintf("\1n\1g\r\n%s%d answer%s to describe your \1hpreferred mate"
2291: "\1n\1g or \1h*\1n\1g for any: "
2292: ,que[i]->que[j].answers > 1 ? "Up to ":""
2293: ,que[i]->que[j].answers,que[i]->que[j].answers > 1 ? "s":"");
2294: if(user.queans[u].pref[j])
2295: bits2ans(user.queans[u].pref[j],str);
2296: getstr(str,que[i]->que[j].answers,K_UPPER|K_LINE|K_EDIT|K_AUTODEL);
2297: if(aborted)
2298: return(0);
2299: truncsp(str);
2300: if(!str[0]) {
2301: j--;
2302: continue; }
2303: y=strlen(str);
2304: for(x=0;x<y;x++)
2305: if(isalpha(str[x]) && str[x]-'A'>que[i]->que[j].answers-1)
2306: break;
2307: if(x<y) {
2308: j--;
2309: continue; }
2310: user.queans[u].pref[j]=ans2bits(str); }
2311: *inuser=user;
2312: return(1);
2313: }
2314:
2315: /* Gets/updates profile from user. Returns 0 if aborted. */
2316:
2317: char get_user_info(user_t *user)
2318: {
2319: char str[128],*p,*hdr;
2320: int i,j,k,x,y;
2321:
2322: while(1) {
2323: checkline();
2324: timeleft=0xffff;
2325: aborted=0;
2326: main_user_info(*user);
2327: CRLF;
2328: bputs("\1n\1h");
2329: bputs("\1b[\1wA\1b] Your name, height, weight, income, location, and "
2330: "text\r\n"
2331: "\1b[\1wB\1b] Your marital status, race, hair color, and eye "
2332: "color\r\n"
2333: "\1b[\1wC\1b] Preferred age, height, weight, location, and income\r\n"
2334: "\1b[\1wD\1b] Preferred sex, marital status, race, hair color, eye "
2335: "color, and zodiac\r\n"
2336: );
2337: for(i=0;i<total_ques;i++) {
2338: if(que[i]->req_age>getage(user->birth))
2339: continue;
2340: bprintf("\1b[\1w%u\1b] \1w%s \1bquestionnaire\1b (%u questions) \1w%s\r\n"
2341: ,i+1,que[i]->desc,que[i]->total_ques
2342: ,user_quenum(que[i]->name,*user)==-1 ? "[Unanswered]":"[Answered]");
2343: }
2344: bprintf("\1b[\1wM\1b] Myers-Briggs personality test (70 questions) "
2345: "\1w[%s]\r\n",user->mbtype[0] ? user->mbtype : "Unanswered");
2346: if(fexist("PURITY.QUE") && purity_age<=getage(user->birth))
2347: bprintf("\1b[\1wP\1b] Purity test \1w(%u%% pure)\r\n"
2348: ,user->purity);
2349: bputs("\r\n\1bWhich or [\1wQ\1b]uit: \1w");
2350: i=getkeys("ABCDMPQ",total_ques);
2351: if(i&0x8000) {
2352: i&=~0x8000;
2353: i--;
2354: get_que(i,user);
2355: continue; }
2356:
2357: switch(i) {
2358: case 'A':
2359: get_your_det(user);
2360: break;
2361: case 'C':
2362: get_pref_det(user);
2363: break;
2364: case 'B':
2365: get_your_multi(user);
2366: break;
2367: case 'D':
2368: get_pref_multi(user);
2369: break;
2370: case 'M':
2371: get_mbtype(user);
2372: break;
2373: case 'P':
2374: get_purity(user);
2375: break;
2376: case 'Q':
2377: return(1); } }
2378: }
2379:
2380: void write_user()
2381: {
2382: char str[256];
2383:
2384: if(auto_update && time(NULL)-useron.updated>(long)auto_update*24L*60L*60L)
2385: useron.updated=time(NULL);
2386: fseek(stream,useron_record*sizeof(user_t),SEEK_SET);
2387: fwrite(&useron,sizeof(user_t),1,stream);
2388: fflush(stream);
2389:
2390: ixb.updated=useron.updated;
2391: if(useron.misc&USER_DELETED)
2392: ixb.number=0;
2393: else
2394: ixb.number=useron.number;
2395: strcpy(str,useron.name);
2396: strupr(str);
2397: ixb.name=crc32(str);
2398: ixb.system=system_crc;
2399: fseek(index,useron_record*sizeof(ixb_t),SEEK_SET);
2400: fwrite(&ixb,sizeof(ixb_t),1,index);
2401: fflush(index);
2402: if(!ixb.number) {
2403: sprintf(str,"%04u.MSG",useron.number);
2404: remove(str); }
2405: }
2406:
2407:
2408: void add_userinfo()
2409: {
2410: static user_t user;
2411: char str[128];
2412: ushort tleft=timeleft;
2413: int i;
2414:
2415: if(!cdt_warning(profile_cdt))
2416: return;
2417: timeleft=0xffff;
2418: user.number=user_number;
2419: user.sex=user_sex;
2420: strcpy(user.name,user_name);
2421: strcpy(user.realname,user_name);
2422: strcpy(user.system,system_name);
2423: strcpy(user.birth,user_birth);
2424: strcpy(user.zipcode,user_zipcode);
2425: sprintf(user.min_zipcode,"%c0000",user_zipcode[0]);
2426: sprintf(user.max_zipcode,"%c9999",user_zipcode[0]);
2427: strcpy(user.location,user_location);
2428: if(user.sex!='M' && user.sex!='F') {
2429: if(yesno("Are you of male gender"))
2430: user.sex='M';
2431: else
2432: user.sex='F'; }
2433: if(!getage(user.birth))
2434: while(1) {
2435: checkline();
2436: cls();
2437: bputs("\1l\1y\1hYour birthdate (MM/DD/YY): ");
2438: if(!getstr(user.birth,8,K_UPPER|K_LINE))
2439: return;
2440: if(getage(user.birth))
2441: break; }
2442:
2443: user.pref_sex=user.sex=='M' ? 'F' : 'M';
2444: user.created=time(NULL);
2445: if(!get_your_det(&user) || !get_your_multi(&user) || !get_pref_multi(&user)
2446: || !get_pref_det(&user)) {
2447: timeleft=tleft;
2448: return; }
2449: for(i=0;i<total_ques;i++) {
2450: aborted=0;
2451: if(que[i]->req_age>getage(user.birth))
2452: continue;
2453: timeleft=0xffff;
2454: cls();
2455: bprintf("\1w\1h%s Questionnaire: \1y%u questions\r\n\r\n"
2456: "\1cAnswers will be viewable by other users.\r\n\r\n"
2457: ,que[i]->desc,que[i]->total_ques);
2458: if(yesno("Continue with questionnaire"))
2459: get_que(i,&user); }
2460: timeleft=0xffff;
2461: get_mbtype(&user);
2462: timeleft=0xffff;
2463: get_purity(&user);
2464: if(!get_user_info(&user)) {
2465: timeleft=tleft;
2466: return; }
2467: user.updated=time(NULL);
2468: useron=user;
2469: bputs("\1n\1h\r\nSaving...");
2470: rewind(index);
2471: while(!feof(index)) {
2472: if(!fread(&ixb,sizeof(ixb_t),1,index))
2473: break;
2474: if(!ixb.number) { /* Deleted User */
2475: fseek(index,ftell(index)-sizeof(ixb_t),SEEK_SET);
2476: break; } }
2477:
2478: useron_record=ftell(index)/sizeof(ixb_t);
2479:
2480: write_user();
2481: adjust_cdt(profile_cdt);
2482:
2483: if(notify_user && notify_user!=user_number) {
2484: sprintf(str,"\1n\1hSMM: \1y%s \1madded %s profile to the Match Maker.\r\n"
2485: ,user_name,user_sex=='M' ? "his":"her");
2486: if(node_dir[0])
2487: putsmsg(notify_user,str);
2488: else
2489: puttgram(notify_user,str); }
2490:
2491: timeleft=tleft;
2492: }
2493:
2494: void delphoto(user_t user)
2495: {
2496: char fname[64],path[128];
2497: int i;
2498: struct ffblk ff;
2499:
2500: if(!(user.misc&USER_PHOTO))
2501: return;
2502: for(i=0;user.system[i];i++)
2503: if(isalnum(user.system[i]))
2504: break;
2505: if(!user.system[i])
2506: fname[0]='~';
2507: else
2508: fname[0]=user.system[i];
2509: for(i=strlen(user.system)-1;i>0;i--)
2510: if(isalnum(user.system[i]))
2511: break;
2512: if(i<=0)
2513: fname[1]='~';
2514: else
2515: fname[1]=user.system[i];
2516: fname[2]=0;
2517: strupr(user.system);
2518: strcat(fname,base41(crc16(user.system),tmp));
2519: strcat(fname,base41(user.number,tmp));
2520: strcat(fname,".*");
2521: strupr(fname);
2522: sprintf(path,"PHOTO\\%s",fname);
2523: i=findfirst(path,&ff,0);
2524: if(i)
2525: return;
2526: sprintf(path,"PHOTO\\%s",ff.ff_name);
2527: if(remove(path))
2528: bprintf("\1r\1h\7%s couldn't be removed!\1n\r\n",path);
2529: else
2530: bprintf("\1r\1hPhoto removed.\r\n");
2531: }
2532:
2533:
2534: void smm_exit()
2535: {
2536: char str[128];
2537: int i;
2538: FILE *in,*out;
2539:
2540: if(io_int) {
2541: io_int=0;
2542: ivhctl(0); }
2543: if(com_port) {
2544: for(i=0;i<5;i++)
2545: if(!rioctl(TXBC)) /* wait for rest of output */
2546: break;
2547: else
2548: mswait(1000);
2549: rioini(0,0); }
2550: if(useron.number) {
2551: useron.lastin=time(NULL);
2552: write_user(); }
2553: if(stream)
2554: fclose(stream);
2555: if(cdt_adjustment) {
2556: if(node_dir[0]) {
2557: sprintf(str,"%sMODUSER.DAT",node_dir);
2558: if((out=fopen(str,"wt"))==NULL) {
2559: bprintf("Error opening %s for write\r\n",str);
2560: return; }
2561: fprintf(out,"%ld",cdt_adjustment);
2562: fclose(out); }
2563: else { /* Write back credits to DOOR.SYS */
2564: strcpy(str,door_sys);
2565: str[strlen(str)-1]='_';
2566: remove(str);
2567: rename(door_sys,str);
2568: if((in=fopen(str,"rb"))==NULL) {
2569: bprintf("Error opening %s for read\r\n",str);
2570: return; }
2571: if((out=fopen(door_sys,"wb"))==NULL) {
2572: bprintf("Error opening %s for write\r\n",door_sys);
2573: return; }
2574: for(i=0;!feof(in);i++) {
2575: if(!fgets(tmp,128,in))
2576: break;
2577: if(i+1==30)
2578: fprintf(out,"%ld\r\n",-(cdt_adjustment/1024L));
2579: else if(i+1==31)
2580: fprintf(out,"%ld\r\n",(user_cdt+cdt_adjustment)/1024L);
2581: else
2582: fprintf(out,"%s",tmp); }
2583: fclose(in);
2584: fclose(out);
2585: remove(str);
2586: } }
2587: }
2588:
2589: time_t checktime()
2590: {
2591: struct tm tm;
2592:
2593: memset(&tm,0,sizeof(tm));
2594: tm.tm_year=94;
2595: tm.tm_mday=1;
2596: return(mktime(&tm)^0x2D24BD00L);
2597: }
2598:
2599: void statusline(void)
2600: {
2601: int col,row;
2602:
2603: col=lclwx();
2604: row=lclwy();
2605: lclxy(1,node_scrnlen);
2606: lclatr(CYAN|HIGH|(BLUE<<4));
2607: lputs(" ");
2608: lprintf("%-25.25s %02d %-25.25s %02d %c %s"
2609: ,user_name,user_level,user_realname[0] ? user_realname : user_location
2610: ,getage(user_birth)
2611: ,user_sex ? user_sex : SP
2612: ,user_phone);
2613: lputc(CLREOL);
2614: lclatr(LIGHTGRAY);
2615: lclxy(col,row);
2616: }
2617:
2618:
2619: int minor_protection(user_t user)
2620: {
2621: if(!user_number || !age_split || SYSOP)
2622: return(0);
2623: if(getage(user_birth)<age_split && getage(user.birth)>=age_split)
2624: return(1);
2625: if(getage(user_birth)>=age_split && getage(user.birth)<age_split)
2626: return(1);
2627: return(0);
2628: }
2629:
2630: void main(int argc, char **argv)
2631: {
2632: char str[512],name[128],desc[128],gotoname[128],*p,ext,ch;
2633: int i,j,k,file,match,found;
2634: uint base=0xffff;
2635: ushort tleft;
2636: long l,offset;
2637: ulong name_crc,sys_crc,*crc_lst,ul;
2638: FILE *fp,*que_lst;
2639: user_t user;
2640: wall_t wall;
2641: struct ffblk ff;
2642:
2643: nodefile=-1;
2644: node_misc=NM_LOWPRIO;
2645: com_port=-1;
2646: com_base=0;
2647: com_irq=com_rate=0;
2648: node_dir[0]=exec_dir[0]=temp_dir[0]=ctrl_dir[0]=door_sys[0]=system_name[0]=0;
2649: sys_name[0]=0;
2650:
2651: p=getenv("SBBSNODE");
2652: if(p) {
2653: strcpy(node_dir,p);
2654: if(node_dir[strlen(node_dir)-1]!='\\')
2655: strcat(node_dir,"\\");
2656: initdata(); }
2657:
2658: gotoname[0]=0;
2659: for(i=1;i<argc;i++) {
2660: if(argv[i][0]=='/') {
2661: switch(toupper(argv[i][1])) {
2662: case 'P':
2663: com_port=atoi(argv[i]+2);
2664: break;
2665: case 'I':
2666: com_irq=atoi(argv[i]+2);
2667: break;
2668: case 'C':
2669: com_base=ahtoul(argv[i]+2);
2670: break;
2671: case 'R':
2672: com_rate=atol(argv[i]+2);
2673: break;
2674: case 'T':
2675: mswtyp=atoi(argv[i]+2);
2676: break;
2677: case 'N':
2678: node_dir[0]=0;
2679: break;
2680: default:
2681: printf("\nusage: SMM [DOOR.SYS] [/option] [/option] [...] [user name]\n");
2682: printf("\n");
2683: printf("where:\n");
2684: printf(" DOOR.SYS is the path and filename of DOOR.SYS\n");
2685: printf("\n");
2686: printf(" /p# sets com port\n");
2687: printf(" /i# sets com irq\n");
2688: printf(" /c# sets com I/O address (or DIGI or FOSSIL)\n");
2689: printf(" /r# sets com rate\n");
2690: printf(" /t# sets time-slice API support\n");
2691: printf("\n");
2692: printf(" user name (if specified) is user to look-up\n");
2693: exit(1); }
2694: continue; }
2695: if(!node_dir[0] && !door_sys[0]) {
2696: strcpy(door_sys,argv[i]);
2697: continue; }
2698: if(gotoname[0])
2699: strcat(gotoname," ");
2700: strcat(gotoname,argv[i]); }
2701:
2702: if(!node_dir[0] && !door_sys[0]) {
2703: printf("\n\7SBBSNODE environment variable not set and DOOR.SYS not "
2704: "specified.\n");
2705: exit(1); }
2706:
2707: if(door_sys[0]) {
2708: #ifdef __TURBOC__
2709: ctrlbrk(cbreakh);
2710: #endif
2711:
2712: #ifdef __WATCOMC__
2713: putenv("TZ=UCT0");
2714: setvbuf(stdout,NULL,_IONBF,0);
2715: setvbuf(stderr,NULL,_IONBF,0);
2716: #endif
2717:
2718: if(setmode(fileno(stderr),O_BINARY)==-1) { /* eliminate LF expansion */
2719: printf("\n\7Can't set stderr to BINARY\n");
2720: exit(1); }
2721:
2722: starttime=time(NULL); /* initialize start time stamp */
2723: wordwrap[0]=0; /* set wordwrap to null */
2724: attr(LIGHTGRAY); /* initialize color and curatr to plain */
2725: mnehigh=LIGHTGRAY|HIGH; /* mnemonics highlight color */
2726: mnelow=GREEN; /* mnemonics normal text color */
2727: sec_warn=180; /* seconds till inactivity warning */
2728: sec_timeout=300; /* seconds till inactivity timeout */
2729: tos=lncntr=0; /* init topofscreen and linecounter to 0 */
2730: lastnodemsg=0; /* Last node to send message to */
2731: aborted=0; /* Ctrl-C hit flag */
2732:
2733: fp=fopen(door_sys,"rb");
2734: if(!fp) {
2735: printf("\n\7ERROR opening %s\n",door_sys);
2736: exit(2); }
2737: user_misc=user_flags2[0]=user_flags3[0]=user_flags4[0]=0;
2738: user_rest[0]=user_exempt[0]=0;
2739: user_sex=user_address[0]=user_zipcode[0]=user_realname[0]=0;
2740: str[0]=0;
2741: fgets(str,81,fp); // 01: COM port - if local
2742: if(com_port==-1)
2743: com_port=atoi(str+3);
2744: str[0]=0;
2745: fgets(str,81,fp); // 02: DCE Rate
2746: user_dce=atoi(str);
2747: fgets(str,81,fp); // 03: Data bits
2748: str[0]=0;
2749: fgets(str,81,fp); // 04: Node num
2750: node_num=atoi(str);
2751: str[0]=0;
2752: fgets(str,81,fp); // 05: DTE rate
2753: if(!com_rate)
2754: com_rate=atol(str);
2755: fgets(str,81,fp); // 06: Screen display
2756: fgets(str,81,fp); // 07: Printer toggle
2757: fgets(str,81,fp); // 08: Page bell
2758: fgets(str,81,fp); // 09: Caller alarm
2759: str[0]=0;
2760: fgets(str,81,fp); // 10: User name
2761: sprintf(user_name,"%.25s",str);
2762: truncsp(user_name);
2763: str[0]=0;
2764: fgets(str,81,fp); // 11: User location
2765: sprintf(user_location,"%.30s",str);
2766: truncsp(user_location);
2767: str[0]=0;
2768: fgets(str,81,fp); // 12: Home phone
2769: sprintf(user_phone,"%.12s",str);
2770: truncsp(user_phone);
2771: fgets(str,81,fp); // 13: Work phone
2772: fgets(str,81,fp); // 14: Password
2773: str[0]=0;
2774: fgets(str,81,fp); // 15: Security Level
2775: user_level=atoi(str);
2776: fgets(str,81,fp); // 16: Total logons
2777: fgets(str,81,fp); // 17: Last on date
2778: str[0]=0;
2779: fgets(str,81,fp); // 18: Time left in seconds
2780: timeleft=atoi(str);
2781: fgets(str,81,fp); // 19: Time left in minutes
2782: str[0]=0;
2783: fgets(str,81,fp); // 20: Graphics
2784: if(!strnicmp(str,"GR",2))
2785: user_misc|=(COLOR|ANSI);
2786: str[0]=0;
2787: fgets(str,81,fp); // 21: Screen length
2788: user_rows=atoi(str);
2789: if(user_rows<10)
2790: user_rows=24;
2791: fgets(str,81,fp); // 22: Expert?
2792: str[0]=0;
2793: fgets(str,81,fp); // 23: Registered conferences
2794: sprintf(user_flags1,"%.26s",str);
2795: truncsp(user_flags1);
2796: fgets(str,81,fp); // 24: Conference came from
2797: str[0]=0;
2798: fgets(str,81,fp); // 25: User's expiration date
2799: user_expire=dstrtounix(str);
2800: str[0]=0;
2801: fgets(str,81,fp); // 26: User's number
2802: user_number=atoi(str);
2803: fgets(str,81,fp); // 27: Default protocol
2804: fgets(str,81,fp); // 28: Total uploads
2805: fgets(str,81,fp); // 29: Total downloads
2806: fgets(str,81,fp); // 30: Kbytes downloaded today
2807: str[0]=0;
2808: fgets(str,81,fp); // 31: Max Kbytes to download today
2809: user_cdt=atol(str)*1024UL;
2810: str[0]=0;
2811: fgets(str,81,fp); // 32: Birthday
2812: truncsp(str);
2813: sprintf(user_birth,"%.8s",str);
2814: fgets(str,81,fp); // 33: Path to MAIN
2815: fgets(str,81,fp); // 34: Path to GEN
2816: str[0]=0;
2817: fgets(str,81,fp); // 35: Sysop's name
2818: sprintf(sys_op,"%.40s",str);
2819: truncsp(sys_op);
2820: fclose(fp);
2821: con_fp=stderr;
2822: if(setmode(fileno(con_fp),O_BINARY)==-1) { /* eliminate LF expansion */
2823: printf("Can't set console output to BINARY\n");
2824: exit(1); }
2825: }
2826:
2827: if(!user_number) {
2828: printf("\7\nERROR: Invalid user number (%u)\n",user_number);
2829: exit(5); }
2830:
2831: if(*(&riobp-1)!=23) {
2832: printf("Wrong rciol.obj\n");
2833: exit(1); }
2834:
2835: node_scrnlen=lclini(0xd<<8); /* Tab expansion, no CRLF expansion */
2836: lclini(node_scrnlen-1);
2837:
2838: if(com_port) {
2839: lprintf("\r\nInitializing COM port %u: ",com_port);
2840: switch(com_base) {
2841: case 0xb:
2842: lputs("PC BIOS");
2843: rioctl(I14PC);
2844: if(!com_irq) com_irq=com_port-1;
2845: break;
2846: case 0xffff:
2847: case 0xd:
2848: lputs("DigiBoard");
2849: rioctl(I14DB);
2850: if(!com_irq) com_irq=com_port-1;
2851: break;
2852: case 0xe:
2853: lputs("PS/2 BIOS");
2854: rioctl(I14PS);
2855: if(!com_irq) com_irq=com_port-1;
2856: break;
2857: case 0xf:
2858: lputs("FOSSIL");
2859: rioctl(I14FO);
2860: if(!com_irq) com_irq=com_port-1;
2861: break;
2862: case 0:
2863: base=com_port;
2864: lputs("UART I/O (BIOS), ");
2865: if(com_irq)
2866: lprintf("IRQ %d",com_irq);
2867: else lputs("default IRQ");
2868: break;
2869: default:
2870: base=com_base;
2871: lprintf("UART I/O %Xh, ",com_base);
2872: if(com_irq)
2873: lprintf("IRQ %d",com_irq);
2874: else lputs("default IRQ");
2875: break; }
2876:
2877: if(base==0xffff)
2878: lprintf(" channel %u",com_irq);
2879: i=rioini(base,com_irq);
2880: if(i) {
2881: lprintf(" - Failed! (%d)\r\n",i);
2882: exit(1); }
2883: if(mdm_misc&MDM_FLOWCTRL)
2884: rioctl(IOSM|CTSCK|RTSCK); /* set rts/cts chk */
2885: if(com_rate)
2886: setbaud((uint)(com_rate&0xffffL));
2887: msr=&riobp-1; }
2888:
2889: /* STATUS LINE */
2890: statusline();
2891:
2892: rioctl(TSTYPE|mswtyp); /* set time-slice API type */
2893:
2894: rioctl(CPTON); /* ctrl-p translation */
2895:
2896: i=INT29L;
2897: if(com_port)
2898: i|=(INT29R|INT16);
2899: ivhctl(i);
2900: io_int=1;
2901:
2902: atexit(smm_exit);
2903:
2904: printf("\r\nSynchronet Match Maker v%s Developed 1995-1997 Rob Swindell\n\n"
2905: ,SMM_VER);
2906:
2907: if(checktime()) {
2908: printf("Time problem!\n");
2909: return; }
2910:
2911: if((file=nopen("SMM.CFG",O_RDONLY))==-1) {
2912: bprintf("\r\n\7Error opening/creating SMM.DAB\r\n");
2913: exit(1); }
2914: if((stream=fdopen(file,"w+b"))==NULL) {
2915: bprintf("\r\n\7Error converting SMM.DAB file handle to stream\r\n");
2916: exit(1); }
2917: str[0]=0;
2918: fgets(str,128,stream);
2919: purity_age=atoi(str);
2920: str[0]=0;
2921: fgets(str,128,stream);
2922: min_age=atoi(str);
2923: str[0]=0;
2924: fgets(str,128,stream);
2925: min_level=atoi(str);
2926:
2927: req_flags1[0]=0;
2928: fgets(req_flags1,128,stream);
2929: req_flags1[27]=0;
2930: truncsp(req_flags1);
2931:
2932: req_flags2[0]=0;
2933: fgets(req_flags2,128,stream);
2934: req_flags2[27]=0;
2935: truncsp(req_flags2);
2936:
2937: req_flags3[0]=0;
2938: fgets(req_flags3,128,stream);
2939: req_flags3[27]=0;
2940: truncsp(req_flags3);
2941:
2942: req_flags4[0]=0;
2943: fgets(req_flags4,128,stream);
2944: req_flags4[27]=0;
2945: truncsp(req_flags4);
2946:
2947: str[0]=0;
2948: fgets(str,128,stream);
2949: profile_cdt=atol(str);
2950: str[0]=0;
2951: fgets(str,128,stream);
2952: telegram_cdt=atol(str);
2953: str[0]=0;
2954: fgets(str,128,stream);
2955: auto_update=atoi(str);
2956: str[0]=0;
2957: fgets(str,128,stream);
2958: notify_user=atoi(str);
2959:
2960: fgets(str,128,stream); // regnum
2961:
2962: str[0]=0;
2963: fgets(str,128,stream);
2964: telegram_level=atoi(str);
2965:
2966: str[0]=0;
2967: fgets(str,128,stream);
2968: que_level=atoi(str);
2969:
2970: str[0]=0;
2971: fgets(str,128,stream);
2972: wall_level=atoi(str);
2973:
2974: str[0]=0;
2975: fgets(str,128,stream);
2976: wall_cdt=atol(str);
2977:
2978: str[0]=0;
2979: fgets(str,128,stream);
2980: que_cdt=atol(str);
2981:
2982: fgets(zmodem_send,128,stream);
2983: if(!zmodem_send[0])
2984: strcpy(zmodem_send,DEFAULT_ZMODEM_SEND);
2985: truncsp(zmodem_send);
2986:
2987: str[0]=0;
2988: fgets(str,128,stream);
2989: smm_misc=atol(str);
2990:
2991: fgets(str,128,stream);
2992: sprintf(system_name,"%.40s",str);
2993: truncsp(system_name);
2994:
2995: fgets(local_view,128,stream);
2996: truncsp(local_view);
2997:
2998: str[0]=0;
2999: fgets(str,128,stream);
3000: sysop_level=atoi(str);
3001: if(!sysop_level)
3002: sysop_level=90;
3003:
3004: str[0]=0;
3005: fgets(str,128,stream);
3006: wall_age=atoi(str);
3007:
3008: str[0]=0;
3009: fgets(str,128,stream);
3010: age_split=atoi(str);
3011:
3012: fclose(stream);
3013:
3014: if(!system_name[0] && sys_name[0])
3015: strcpy(system_name,sys_name);
3016: if(!system_name[0]) {
3017: printf("\7\nERROR: System name not specified\n");
3018: exit(3) ; }
3019:
3020: sprintf(str,"%.25s",system_name);
3021: strupr(str);
3022: system_crc=crc32(str);
3023:
3024: if((file=open("SMM.DAB",O_RDWR|O_BINARY|SH_DENYNO|O_CREAT
3025: ,S_IWRITE|S_IREAD))==-1) {
3026: bprintf("\r\n\7Error opening/creating SMM.DAB\r\n");
3027: exit(1); }
3028: if((stream=fdopen(file,"w+b"))==NULL) {
3029: bprintf("\r\n\7Error converting SMM.DAB file handle to stream\r\n");
3030: exit(1); }
3031: setvbuf(stream,0L,_IOFBF,4096);
3032:
3033: if((file=open("SMM.IXB",O_RDWR|O_BINARY|SH_DENYNO|O_CREAT
3034: ,S_IWRITE|S_IREAD))==-1) {
3035: bprintf("\r\n\7Error opening/creating SMM.IXB\r\n");
3036: exit(1); }
3037: if((index=fdopen(file,"w+b"))==NULL) {
3038: bprintf("\r\n\7Error converting SMM.IXB file handle to stream\r\n");
3039: exit(1); }
3040: setvbuf(stream,0L,_IOFBF,1024);
3041:
3042: trashfile=NULL;
3043: if((file=open("SMM.CAN",O_RDONLY|SH_DENYNO))!=-1) {
3044: trashfile=fdopen(file,"rb");
3045: setvbuf(trashfile,NULL,_IOFBF,4096); }
3046:
3047: total_ques=0;
3048: i=nopen("QUE.LST",O_RDONLY);
3049: if(i!=-1)
3050: que_lst=fdopen(i,"rb");
3051: else
3052: que_lst=NULL;
3053: i=0;
3054: while(que_lst && !feof(que_lst) && i<5) {
3055: if(!fgets(name,81,que_lst))
3056: break;
3057: truncsp(name);
3058: strupr(name);
3059: sprintf(str,"%s.QUE",name);
3060: if(!fgets(desc,81,que_lst))
3061: break;
3062: truncsp(desc);
3063: if(!fgets(tmp,81,que_lst))
3064: break;
3065: truncsp(tmp);
3066: if((file=nopen(str,O_RDONLY))!=-1) {
3067: fp=fdopen(file,"rb");
3068: total_ques++;
3069: if((que[i]=(questionnaire_t *)MALLOC(sizeof(questionnaire_t)))==NULL) {
3070: bprintf("Can't malloc questionnaires!\r\n");
3071: exit(1); }
3072: sprintf(que[i]->name,"%.8s",name);
3073: sprintf(que[i]->desc,"%.25s",desc);
3074: que[i]->req_age=atoi(tmp);
3075: fgets(str,128,fp);
3076: que[i]->total_ques=atoi(str);
3077: if(que[i]->total_ques<1 || que[i]->total_ques>20) {
3078: bprintf("Invalid number of questions (%d) in questionnaire #%d\r\n"
3079: ,que[i]->total_ques,i+1);
3080: exit(1); }
3081: for(j=0;j<que[i]->total_ques;j++) {
3082: if(!fgets(str,128,fp))
3083: break;
3084: truncsp(str);
3085: if(!str[0])
3086: break;
3087: str[80]=0;
3088: strcpy(que[i]->que[j].txt,str);
3089: fgets(str,128,fp);
3090: que[i]->que[j].answers=atoi(str);
3091: if(que[i]->que[j].answers<1 || que[i]->que[j].answers>16) {
3092: bprintf("Invalid number of answers (%d) in question #%d "
3093: "of questionnaire #%d\r\n"
3094: ,que[i]->que[j].answers,j+1,i+1);
3095: exit(1); }
3096: fgets(str,128,fp);
3097: que[i]->que[j].allowed=atoi(str);
3098: for(k=0;k<que[i]->que[j].answers;k++) {
3099: if(!fgets(str,128,fp))
3100: break;
3101: truncsp(str);
3102: if(!str[0])
3103: break;
3104: str[60]=0;
3105: strcpy(que[i]->que[j].ans[k],str); }
3106: que[i]->que[j].answers=k; }
3107:
3108: que[i]->total_ques=j; }
3109: fclose(fp);
3110: i++; }
3111: fclose(que_lst);
3112:
3113: lncntr=0;
3114: getsmsg(user_number);
3115: if(lncntr)
3116: pause();
3117:
3118: memset(&useron,0,sizeof(user_t));
3119:
3120: atexit(smm_exit);
3121:
3122: bputs("\1n\1hSearching for your profile...");
3123: rewind(index);
3124: while(!feof(index)) {
3125: if(!fread(&ixb,sizeof(ixb_t),1,index))
3126: break;
3127: if(ixb.system==system_crc && ixb.number==user_number) {
3128: useron_record=(ftell(index)-sizeof(ixb_t))/sizeof(ixb_t);
3129: fseek(stream,useron_record*sizeof(user_t),SEEK_SET);
3130: fread(&user,sizeof(user_t),1,stream);
3131: if(stricmp(user.realname,user_name)) { /* new name, so delete it */
3132: user.misc|=USER_DELETED;
3133: fseek(stream,ftell(stream)-sizeof(user_t),SEEK_SET);
3134: fwrite(&user,sizeof(user_t),1,stream);
3135: fseek(stream,0,SEEK_CUR);
3136: fseek(index,ftell(index)-sizeof(ixb_t),SEEK_SET);
3137: ixb.number=0;
3138: fwrite(&ixb,sizeof(ixb_t),1,index);
3139: sprintf(str,"%04u.MSG",user_number);
3140: remove(str);
3141: continue; }
3142: useron=user; /* name matches, same user */
3143: break; } }
3144: fflush(stream);
3145: fflush(index);
3146: CRLF;
3147:
3148: if(useron.number && useron.sex!='M' && useron.sex!='F') {
3149: if(yesno("Are you of male gender"))
3150: useron.sex='M';
3151: else
3152: useron.sex='F';
3153: write_user();
3154: user_sex=useron.sex; }
3155:
3156: if(!useron.number && user_sex!='M' && user_sex!='F' && can_add()) {
3157: if(yesno("Are you of male gender"))
3158: user_sex='M';
3159: else
3160: user_sex='F'; }
3161:
3162: if(!useron.number && can_add()) {
3163: sprintf(str,"%04u.MSG",user_number);
3164: remove(str);
3165: printfile("SMM_LOGO.ASC");
3166: if(yesno("\r\nYour profile doesn't exist. Create it now"))
3167: add_userinfo(); }
3168:
3169: if(gotoname[0]) {
3170: strupr(gotoname);
3171: name_crc=crc32(gotoname);
3172: rewind(index);
3173: i=0;
3174: while(!feof(index)) {
3175: if(!fread(&ixb,sizeof(ixb_t),1,index))
3176: break;
3177: if(!ixb.number) /* DELETED */
3178: continue;
3179: if(ixb.name!=name_crc)
3180: continue;
3181: fseek(stream
3182: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
3183: *sizeof(user_t),SEEK_SET);
3184: if(!fread(&user,sizeof(user_t),1,stream))
3185: continue;
3186: if(minor_protection(user))
3187: continue;
3188: i=1;
3189: if(!long_user_info(user))
3190: break; }
3191: if(!i) {
3192: bprintf("\r\n\1n\1h%s \1rnot found.\r\n",gotoname);
3193: pause(); }
3194: return; }
3195:
3196: /*********************************************/
3197: /* ALL User Messages (from Digital Dynamics) */
3198: /*********************************************/
3199: for(i=findfirst("ALL*.MSG",&ff,0);!i;i=findnext(&ff)) {
3200: if((j=nopen(ff.ff_name,O_RDONLY))==-1) {
3201: bprintf("\1n\1r\1hCan't open \1w%s\r\n",ff.ff_name);
3202: pause();
3203: continue; }
3204: if((fp=fdopen(j,"rb"))==NULL) {
3205: bprintf("\1n\1r\1hCan't fdopen \1w%s\r\n",ff.ff_name);
3206: pause();
3207: continue; }
3208: str[0]=0;
3209: fgets(str,128,fp);
3210: truncsp(str);
3211: ul=ahtoul(str); /* Expiration date */
3212: ul^=0x305F6C81UL;
3213: attr(LIGHTGRAY);
3214: cls();
3215: while(!feof(fp)) {
3216: if(!fgets(str,128,fp))
3217: break;
3218: bputs(str); }
3219: fclose(fp);
3220: CRLF;
3221: if(ul<=time(NULL))
3222: remove(ff.ff_name); }
3223:
3224: /**************************************************/
3225: /* One-time User Messages (from Digital Dynamics) */
3226: /**************************************************/
3227: for(i=findfirst("ONE*.MSG",&ff,0);!i;i=findnext(&ff)) {
3228: if(fdate_dir(ff.ff_name)<useron.lastin)
3229: continue;
3230: if((j=nopen(ff.ff_name,O_RDONLY))==-1) {
3231: bprintf("\1n\1r\1hCan't open \1w%s\r\n",ff.ff_name);
3232: pause();
3233: continue; }
3234: if((fp=fdopen(j,"rb"))==NULL) {
3235: bprintf("\1n\1r\1hCan't fdopen \1w%s\r\n",ff.ff_name);
3236: pause();
3237: continue; }
3238: str[0]=0;
3239: fgets(str,128,fp);
3240: truncsp(str);
3241: ul=ahtoul(str); /* Expiration date */
3242: ul^=0x305F6C81UL;
3243: attr(LIGHTGRAY);
3244: cls();
3245: while(!feof(fp)) {
3246: if(!fgets(str,128,fp))
3247: break;
3248: bputs(str); }
3249: fclose(fp);
3250: CRLF;
3251: if(ul<=time(NULL))
3252: remove(ff.ff_name); }
3253:
3254: /******************************************/
3255: /* Sysop Messages (from Digital Dynamics) */
3256: /******************************************/
3257: for(i=findfirst("SYS*.MSG",&ff,0);SYSOP && !i;i=findnext(&ff)) {
3258: if((j=nopen(ff.ff_name,O_RDONLY))==-1) {
3259: bprintf("\1n\1r\1hCan't open \1w%s\r\n",ff.ff_name);
3260: pause();
3261: continue; }
3262: if((fp=fdopen(j,"rb"))==NULL) {
3263: bprintf("\1n\1r\1hCan't fdopen \1w%s\r\n",ff.ff_name);
3264: pause();
3265: continue; }
3266: str[0]=0;
3267: fgets(str,128,fp);
3268: truncsp(str);
3269: ul=ahtoul(str); /* Expiration date */
3270: ul^=0x305F6C81UL;
3271: attr(LIGHTGRAY);
3272: cls();
3273: while(!feof(fp)) {
3274: if(!fgets(str,128,fp))
3275: break;
3276: bputs(str); }
3277: fclose(fp);
3278: CRLF;
3279: if(ul<=time(NULL) || !noyes("Delete message"))
3280: remove(ff.ff_name); }
3281:
3282: statusline();
3283: while(1) {
3284: checkline();
3285: aborted=0;
3286: attr(LIGHTGRAY);
3287: cls();
3288:
3289: bprintf("\1n \1b\1hSynchronet \1cMatch Maker \1bv%s (XSDK v%s) "
3290: "Developed 1995-1997 Rob Swindell\1n\r\n\r\n",SMM_VER,xsdk_ver);
3291: printfile("SMM_LOGO.ASC");
3292: CRLF;
3293:
3294: l=filelength(fileno(stream));
3295: if(l<0) l=0;
3296: sprintf(str,"\1n\1cThere are \1h%lu\1n\1c entries in the user profile "
3297: "database.\r\n",l/(long)sizeof(user_t));
3298: center(str);
3299:
3300: sprintf(str,"%04u.MSG",user_number);
3301: if(fexist(str))
3302: center("\1h\1mYou have awaiting telegrams!\r\n");
3303:
3304: if(flength("WALL.DAB")>0)
3305: center("\1h\1cThere is writing on the Wall.\r\n");
3306:
3307: if(!useron.number)
3308: center("\1h\1rYou have not yet created a profile!\r\n");
3309:
3310: printfile("SMM_MAIN.ASC");
3311:
3312: nodesync(); /* Display any waiting messages */
3313:
3314: bprintf("\r\n%32s\1b\1hWhich or [\1wQ\1b]uit: \1h\1w",nulstr);
3315: ch=getkey(K_UPPER);
3316: // bprintf("%c\r\n",ch);
3317: bputs("\r\1>");
3318: switch(ch) {
3319: case '?':
3320: break;
3321: case '*':
3322: if(!SYSOP)
3323: break;
3324: bputs("\1n\1hSearching...");
3325: rewind(stream);
3326: while(!feof(stream) && !aborted) {
3327: if(!fread(&user,sizeof(user_t),1,stream))
3328: break;
3329: if(user.misc&USER_DELETED) {
3330: sprintf(str,"\r\nUndelete \1c%s \1b(\1c%s@%s\1b)"
3331: ,user.name,user.realname,user.system);
3332: if(!yesno(str))
3333: continue;
3334: fseek(stream,ftell(stream)-sizeof(user_t),SEEK_SET);
3335: user.misc&=~USER_DELETED;
3336: fwrite(&user,sizeof(user_t),1,stream);
3337: fseek(stream,0,SEEK_CUR);
3338: fseek(index
3339: ,((ftell(stream)-sizeof(user_t))/sizeof(user_t))
3340: *sizeof(ixb_t),SEEK_SET);
3341: strcpy(str,user.name);
3342: strupr(str);
3343: ixb.name=crc32(str);
3344: sprintf(str,"%.25s",user.system);
3345: strupr(str);
3346: ixb.system=crc32(str);
3347: ixb.updated=user.updated;
3348: ixb.number=user.number;
3349: fwrite(&ixb,sizeof(ixb_t),1,index);
3350: } }
3351: fflush(stream);
3352: fflush(index);
3353: break;
3354: case '!':
3355: if(!SYSOP)
3356: break;
3357: cls();
3358: bputs("\1n\1hSystems Participating in Your Database:\r\n\r\n\1m");
3359: crc_lst=NULL;
3360: j=0;
3361: rewind(stream);
3362: while(!feof(stream) && !aborted) {
3363: if(!fread(&user,sizeof(user_t),1,stream))
3364: break;
3365: if(user.misc&USER_DELETED || !(user.misc&USER_FROMSMB))
3366: continue;
3367: if(!smm_pause)
3368: lncntr=0;
3369: sprintf(str,"%.25s",user.system);
3370: strupr(str);
3371: sys_crc=crc32(str);
3372: for(i=0;i<j;i++)
3373: if(sys_crc==crc_lst[i])
3374: break;
3375: if(i==j) {
3376: crc_lst=REALLOC(crc_lst,(j+1)*sizeof(ulong));
3377: if(crc_lst==NULL) {
3378: printf("REALLOC error!\n");
3379: pause();
3380: break; }
3381: crc_lst[j++]=sys_crc;
3382: bprintf("%s\r\n",user.system); } }
3383: if(crc_lst)
3384: FREE(crc_lst);
3385: if(j)
3386: bprintf("\1n\r\n\1h%u systems listed.\r\n",j);
3387: pause();
3388: break;
3389: case '\\':
3390: if(!SYSOP)
3391: break;
3392: bprintf("Rebuilding Index...");
3393: rewind(stream);
3394: rewind(index);
3395: while(!feof(stream)) {
3396: if(!fread(&user,sizeof(user_t),1,stream))
3397: break;
3398: if(user.misc&USER_DELETED)
3399: ixb.number=0;
3400: else
3401: ixb.number=user.number;
3402: strupr(user.name);
3403: ixb.name=crc32(user.name);
3404: strupr(user.system);
3405: user.system[25]=0;
3406: ixb.system=crc32(user.system);
3407: ixb.updated=user.updated;
3408: fwrite(&ixb,sizeof(ixb_t),1,index); }
3409: break;
3410: case 'R':
3411: if(useron.number) {
3412: bputs("\1y\1hMinimum match percentage: \1w");
3413: sprintf(str,"%u",useron.min_match);
3414: if(!getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL) || aborted)
3415: break;
3416: useron.min_match=atoi(str);
3417: if(useron.min_match>100)
3418: useron.min_match=100; }
3419: rewind(stream);
3420: bprintf("\1n\1l\1hSearching...");
3421: while(!feof(stream) && !aborted) {
3422: if(!fread(&user,sizeof(user_t),1,stream))
3423: break;
3424: if(user.misc&USER_DELETED)
3425: continue;
3426: if(minor_protection(user))
3427: continue;
3428: if(useron.min_match && useron.number) {
3429: match=total_match(useron,user);
3430: if(match<useron.min_match)
3431: continue; }
3432: if(!long_user_info(user))
3433: break;
3434: if(!smm_pause)
3435: lncntr=0;
3436: bprintf("\1n\1l\1hSearching..."); }
3437: break;
3438: case 'F':
3439: bputs("\1y\1hText to search for: ");
3440: if(!getstr(str,25,K_UPPER|K_LINE))
3441: break;
3442: ext=yesno("\r\nDisplay extended profiles");
3443: cls();
3444: if(!smm_pause && !ext)
3445: printfile("LIST_HDR.ASC");
3446: rewind(stream);
3447: i=0;
3448: while(!aborted) {
3449: bprintf("\1n\1l\1hSearching...");
3450: while(!feof(stream) && !aborted) {
3451: if(!fread(&user,sizeof(user_t),1,stream))
3452: break;
3453: if(user.misc&USER_DELETED)
3454: continue;
3455: if(minor_protection(user))
3456: continue;
3457: tmpuser=user;
3458: sprintf(tmp,"%lu",user.number);
3459: strupr(user.name);
3460: strupr(user.realname);
3461: strupr(user.system);
3462: strupr(user.location);
3463: strupr(user.note[0]);
3464: strupr(user.note[1]);
3465: strupr(user.note[2]);
3466: strupr(user.note[3]);
3467: strupr(user.note[4]);
3468: if(strstr(user.name,str)
3469: || strstr(user.location,str)
3470: || strstr(user.mbtype,str)
3471: || strstr(user.note[0],str)
3472: || strstr(user.note[1],str)
3473: || strstr(user.note[2],str)
3474: || strstr(user.note[3],str)
3475: || strstr(user.note[4],str)
3476: || (SYSOP && strstr(user.realname,str))
3477: || (SYSOP && strstr(user.system,str))
3478: || (SYSOP && !strcmp(tmp,str))
3479: ) {
3480: i=1;
3481: if(ext && !long_user_info(tmpuser))
3482: break;
3483: if(!ext && short_user_info(tmpuser)==0)
3484: break;
3485: if(!smm_pause)
3486: lncntr=0; } }
3487: if(aborted || ext || !lncntr)
3488: break;
3489: user.number=0;
3490: if(short_user_info(user)>=0)
3491: break; }
3492: if(!i)
3493: bprintf("\r\n\1n\1h%s \1rnot found.\r\n",str);
3494: break;
3495: case 'G':
3496: bputs("\1y\1hUser name: ");
3497: if(!getstr(str,25,K_UPPER|K_LINE))
3498: break;
3499: truncsp(str);
3500: name_crc=crc32(str);
3501: rewind(index);
3502: i=0;
3503: while(!feof(index)) {
3504: if(!fread(&ixb,sizeof(ixb_t),1,index))
3505: break;
3506: if(!ixb.number) /* DELETED */
3507: continue;
3508: if(ixb.name!=name_crc)
3509: continue;
3510: fseek(stream
3511: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
3512: *sizeof(user_t),SEEK_SET);
3513: if(!fread(&user,sizeof(user_t),1,stream))
3514: continue;
3515: if(minor_protection(user))
3516: continue;
3517: i=1;
3518: if(!long_user_info(user))
3519: break; }
3520: if(!i)
3521: bprintf("\r\n\1n\1h%s \1rnot found.\r\n",str);
3522: break;
3523: case 'L':
3524: if(useron.number) {
3525: bputs("\1y\1hMinimum match percentage: \1w");
3526: sprintf(str,"%u",useron.min_match);
3527: if(!getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL) || aborted)
3528: break;
3529: useron.min_match=atoi(str);
3530: if(useron.min_match>100)
3531: useron.min_match=100; }
3532: cls();
3533: if(!smm_pause)
3534: printfile("LIST_HDR.ASC");
3535: rewind(stream);
3536: while(!aborted) {
3537: while(!feof(stream) && !aborted) {
3538: if(!fread(&user,sizeof(user_t),1,stream))
3539: break;
3540: if(user.misc&USER_DELETED)
3541: continue;
3542: if(minor_protection(user))
3543: continue;
3544: if(useron.min_match && useron.number) {
3545: match=total_match(useron,user);
3546: if(match<useron.min_match)
3547: continue; }
3548: if(!short_user_info(user))
3549: break;
3550: if(!smm_pause)
3551: lncntr=0; }
3552: if(aborted || !lncntr)
3553: break;
3554: user.number=0;
3555: if(short_user_info(user)>=0)
3556: break; }
3557: break;
3558:
3559: case 'N':
3560: while(1) {
3561: checkline();
3562: bputs("\1y\1hLast update (MM/DD/YY): ");
3563: if(useron.number)
3564: unixtodstr(useron.lastin,str);
3565: else
3566: str[0]=0;
3567: if(!getstr(str,8,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
3568: break;
3569: if(isdigit(str[0]) && isdigit(str[1]) && str[2]=='/'
3570: && isdigit(str[3]) && isdigit(str[4]) && str[5]=='/'
3571: && isdigit(str[6]) && isdigit(str[7]))
3572: break;
3573: bputs("\r\n\1h\1rInvalid date!\r\n\r\n"); }
3574: if(!str[0] || aborted)
3575: break;
3576: l=dstrtounix(str);
3577: if(useron.number) {
3578: bputs("\1y\1h\r\nMinimum match percentage: \1w");
3579: sprintf(str,"%u",useron.min_match);
3580: if(!getstr(str,3,K_NUMBER|K_EDIT|K_AUTODEL) || aborted)
3581: break;
3582: useron.min_match=atoi(str);
3583: if(useron.min_match>100)
3584: useron.min_match=100; }
3585: ext=!noyes("\r\nDisplay extended profiles");
3586: if(aborted)
3587: break;
3588: cls();
3589: if(!ext && !smm_pause)
3590: printfile("LIST_HDR.ASC");
3591: rewind(index);
3592: while(!aborted) {
3593: while(!feof(index) && !aborted) {
3594: if(!smm_pause)
3595: lncntr=0;
3596: if(!fread(&ixb,sizeof(ixb_t),1,index))
3597: break;
3598: if(!ixb.number) /* DELETED */
3599: continue;
3600: if(ixb.updated>=l) {
3601: fseek(stream
3602: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
3603: *sizeof(user_t),SEEK_SET);
3604: if(!fread(&user,sizeof(user_t),1,stream))
3605: continue;
3606: if(minor_protection(user))
3607: continue;
3608: if(useron.min_match && useron.number) {
3609: match=total_match(useron,user);
3610: if(match<useron.min_match)
3611: continue; }
3612: if(ext && !long_user_info(user))
3613: break;
3614: if(!ext && short_user_info(user)==0)
3615: break;
3616: continue; } }
3617: if(aborted || ext || !lncntr)
3618: break;
3619: user.number=0;
3620: if(short_user_info(user)>=0)
3621: break; }
3622: break;
3623:
3624: case 'U':
3625: case 'W': /* Create/Edit Profile */
3626: if(!can_add()) {
3627: bprintf("\1h\1rYou have insufficient access to create a "
3628: "profile.\r\n\r\n");
3629: break; }
3630:
3631: if(!useron.number) {
3632: add_userinfo();
3633: break; }
3634:
3635: user=useron;
3636: tleft=timeleft;
3637: if(!get_user_info(&user)) {
3638: timeleft=tleft;
3639: break; }
3640:
3641: if(!memcmp(&user,&useron,sizeof(user_t))) {
3642: timeleft=tleft;
3643: break; }
3644:
3645: if(!yesno("Save changes")) {
3646: timeleft=tleft;
3647: break; }
3648: timeleft=tleft;
3649: user.updated=time(NULL);
3650: useron=user;
3651: write_user();
3652: break;
3653:
3654: case 'D':
3655: if(SYSOP) {
3656: bputs("Name to Delete: ");
3657: if(useron.number) {
3658: strcpy(str,useron.name);
3659: strupr(str); }
3660: else
3661: str[0]=0;
3662: getstr(str,25,K_UPPER|K_LINE|K_EDIT|K_AUTODEL);
3663: rewind(stream);
3664: while(!feof(stream)) {
3665: if(!fread(&user,sizeof(user_t),1,stream))
3666: break;
3667: strcpy(tmp,user.name);
3668: strupr(tmp);
3669: if(!(user.misc&USER_DELETED) && strstr(tmp,str)) {
3670: sprintf(tmp,"Delete %s (%s@%s)"
3671: ,user.name,user.realname,user.system);
3672: i=noyes(tmp);
3673: if(aborted)
3674: break;
3675: if(i)
3676: continue;
3677: fseek(stream,ftell(stream)-sizeof(user_t),SEEK_SET);
3678: fseek(index
3679: ,((ftell(stream)-sizeof(user_t))/sizeof(user_t))
3680: *sizeof(ixb_t),SEEK_SET);
3681: user.misc|=USER_DELETED;
3682: fwrite(&user,sizeof(user_t),1,stream);
3683: fseek(stream,0,SEEK_CUR);
3684: memset(&ixb,0,sizeof(ixb_t));
3685: fwrite(&ixb,sizeof(ixb_t),1,index);
3686: fflush(stream);
3687: fflush(index);
3688: delphoto(user);
3689: if(user.number==user_number
3690: && !stricmp(user.system,system_name))
3691: useron.number=0;
3692: break; } }
3693: if(aborted)
3694: break;
3695: break; }
3696: if(!useron.number) {
3697: bputs("\1h\1rYour profile doesn't exist.\r\n\r\n");
3698: break; }
3699: if(noyes("Are you sure you want to delete your profile"))
3700: break;
3701: if(!cdt_warning(-profile_cdt))
3702: break;
3703: sprintf(str,"%04u.MSG",user_number);
3704: remove(str);
3705: fseek(stream,useron_record*sizeof(user_t),SEEK_SET);
3706: useron.misc|=USER_DELETED;
3707: fwrite(&useron,sizeof(user_t),1,stream);
3708: fflush(stream);
3709: memset(&ixb,0,sizeof(ixb_t));
3710: fseek(index,useron_record*sizeof(ixb_t),SEEK_SET);
3711: fwrite(&ixb,sizeof(ixb_t),1,index);
3712: fflush(index);
3713: delphoto(user);
3714: useron.number=0;
3715: aborted=0;
3716: bputs("\r\n\1h\1r\1iProfile deleted.\r\n");
3717: adjust_cdt(-profile_cdt);
3718: break;
3719: case 'P':
3720: smm_pause=!smm_pause;
3721: bprintf("\1r\1hScreen pause is now \1w%s\r\n\r\n"
3722: ,smm_pause ? "ON":"OFF");
3723: break;
3724: case 'M':
3725: mbtype_desc(useron.mbtype);
3726: break;
3727: case 'H':
3728: cls();
3729: printfile("SMM_HELP.ASC");
3730: break;
3731: case 'O':
3732: if(noyes("Hang-up now"))
3733: break;
3734: dtr(5);
3735: if(node_dir) {
3736: sprintf(str,"%sHANGUP.NOW",node_dir);
3737: fopen(str,"wb");
3738: nodesync(); }
3739: return;
3740: case 'S':
3741: bputs("\1y\1hUser name: ");
3742: if(!getstr(str,25,K_UPPER|K_LINE))
3743: break;
3744: truncsp(str);
3745: name_crc=crc32(str);
3746: rewind(index);
3747: i=0;
3748: while(!feof(index)) {
3749: if(!fread(&ixb,sizeof(ixb_t),1,index))
3750: break;
3751: if(!ixb.number) /* DELETED */
3752: continue;
3753: if(ixb.name!=name_crc)
3754: continue;
3755: fseek(stream
3756: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
3757: *sizeof(user_t),SEEK_SET);
3758: if(!fread(&user,sizeof(user_t),1,stream))
3759: continue;
3760: if(minor_protection(user))
3761: continue;
3762: i=1;
3763: if(send_telegram(user))
3764: break; }
3765: if(!i)
3766: bprintf("\r\n\1n\1h%s \1rnot found.\r\n",str);
3767: break;
3768: case 'T':
3769: sprintf(str,"%04u.MSG",user_number);
3770: if(!fexist(str)) {
3771: bputs("\1r\1hYou have no telegrams waiting.\r\n\r\n");
3772: break; }
3773: cls();
3774: printfile(str);
3775: if(noyes("\r\nDelete all telegrams waiting for you"))
3776: break;
3777: remove(str);
3778: break;
3779: case 'V': /* Visit the wall */
3780: if(getage(user_birth)<wall_age && !SYSOP) {
3781: bputs("\1r\1hSorry, you're too young to view the wall.\r\n");
3782: pause();
3783: break; }
3784: while(1) {
3785: checkline();
3786: bputs("\1y\1hView writing since (MM/DD/YY): ");
3787: if(useron.number)
3788: unixtodstr(useron.lastin,str);
3789: else
3790: str[0]=0;
3791: if(!getstr(str,8,K_UPPER|K_LINE|K_EDIT|K_AUTODEL))
3792: break;
3793: if(isdigit(str[0]) && isdigit(str[1]) && str[2]=='/'
3794: && isdigit(str[3]) && isdigit(str[4]) && str[5]=='/'
3795: && isdigit(str[6]) && isdigit(str[7]))
3796: break;
3797: bputs("\r\n\1h\1rInvalid date!\r\n\r\n"); }
3798: if(aborted)
3799: break;
3800: l=dstrtounix(str);
3801: ext=yesno("\r\nDisplay extended information when available");
3802: if(aborted)
3803: break;
3804: strcpy(str,"WALL.DAB");
3805: if((file=sopen(str,O_RDWR|O_BINARY|O_CREAT,SH_DENYNO
3806: ,S_IREAD|S_IWRITE))==-1) {
3807: bprintf("\r\nError opening %s\r\n",str);
3808: break; }
3809: cls();
3810: offset=0L;
3811: while(!eof(file) && !aborted) {
3812: if(read(file,&wall,sizeof(wall_t))!=sizeof(wall_t))
3813: break;
3814: if(wall.imported<l)
3815: continue;
3816: strcpy(str,wall.name);
3817: strupr(str);
3818: name_crc=crc32(str);
3819: sprintf(str,"%.25s",wall.system);
3820: strupr(str);
3821: sys_crc=crc32(str);
3822: rewind(index);
3823: i=0;
3824: user.sex=0;
3825: while(ext && !feof(index) && !aborted) {
3826: if(!fread(&ixb,sizeof(ixb_t),1,index))
3827: break;
3828: if(!ixb.number) /* DELETED */
3829: continue;
3830: if(ixb.name!=name_crc || ixb.system!=sys_crc)
3831: continue;
3832: fseek(stream
3833: ,((ftell(index)-sizeof(ixb_t))/sizeof(ixb_t))
3834: *sizeof(user_t),SEEK_SET);
3835: if(!fread(&user,sizeof(user_t),1,stream))
3836: continue;
3837: if(minor_protection(user))
3838: break;
3839: main_user_info(user);
3840: if(useron.number) {
3841: CRLF;
3842: bprintf("\1h\1mThis user meets your profile "
3843: "preferences:\1w%3u%% "
3844: ,basic_match(useron,user));
3845: bprintf("\1n\1gCreated: \1h%s\r\n"
3846: ,unixtodstr(user.created,str));
3847: bprintf("\1h\1mYou meet this user's profile "
3848: "preferences:\1w%3u%% "
3849: ,basic_match(user,useron));
3850: bprintf("\1n\1gUpdated: \1h%s\r\n"
3851: ,unixtodstr(user.updated,str)); }
3852:
3853: i=1;
3854: CRLF;
3855: break; }
3856: if(!i) {
3857: if(ext)
3858: cls();
3859: bprintf("\1n\1h%s ",wall.name); }
3860: bprintf("\1n\1h\1cWrote on %s:\r\n"
3861: ,timestr(&wall.written));
3862: for(j=0;j<5;j++) {
3863: if(!wall.text[j][0])
3864: break;
3865: bprintf("\1n\1%c%5s%s\r\n"
3866: ,user.sex=='F'?'m':'g',"",wall.text[j]); }
3867: if(aborted)
3868: break;
3869: if(ext) {
3870: nodesync();
3871: if(i) {
3872: bputs(PrevReadSendQuitOrMore);
3873: ch=getkey(K_UPPER);
3874: if(ch=='R')
3875: long_user_info(user);
3876: if(ch=='S')
3877: send_telegram(user);
3878: if(ch=='R' || ch=='S') /* Don't move forward */
3879: lseek(file,tell(file)-sizeof(wall_t),SEEK_SET); }
3880: else {
3881: bputs("\r\n\1n\1hProfile not found.\r\n\r\n");
3882: bputs("\1b[\1cP\1b]revious, [\1cQ\1b]uit, "
3883: "or [\1cM\1b]ore: \1c");
3884: ch=getkey(K_UPPER); }
3885: if(ch=='P') {
3886: lseek(file,offset,SEEK_SET);
3887: if(tell(file))
3888: lseek(file,tell(file)-sizeof(wall_t),SEEK_SET);
3889: offset=tell(file);
3890: continue; }
3891: if(ch=='Q') {
3892: cls();
3893: break; }
3894: offset=tell(file); }
3895: else if(lncntr+7>=user_rows || eof(file)) {
3896: lncntr=0;
3897: bputs(PrevReadSendQuitOrMore);
3898: ch=getkey(K_UPPER);
3899: if(ch=='Q')
3900: break;
3901: else if(ch=='S' || ch=='R') {
3902: bprintf("\1n\r\1>\1y\1hUser name: ");
3903: if(getstr(name,25,K_UPPER|K_LINE|K_NOCRLF)) {
3904: truncsp(name);
3905: name_crc=crc32(name);
3906: rewind(index);
3907: i=0;
3908: while(!feof(index)) {
3909: if(!fread(&ixb,sizeof(ixb_t),1,index))
3910: break;
3911: if(!ixb.number) /* DELETED */
3912: continue;
3913: if(ixb.name!=name_crc)
3914: continue;
3915: fseek(stream
3916: ,((ftell(index)
3917: -sizeof(ixb_t))/sizeof(ixb_t))
3918: *sizeof(user_t),SEEK_SET);
3919: if(!fread(&user,sizeof(user_t),1,stream))
3920: continue;
3921: if(minor_protection(user))
3922: continue;
3923: i=1;
3924: if(ch=='S' && send_telegram(user))
3925: break;
3926: if(ch=='R' && !long_user_info(user))
3927: break; }
3928: if(!i)
3929: bprintf("\r\n\1n\1h%s \1rnot found.\r\n",name);
3930: }
3931: lseek(file,offset,SEEK_SET); }
3932: else if(ch=='P') {
3933: lseek(file,offset,SEEK_SET);
3934: for(i=0;i<4;i++)
3935: if(tell(file))
3936: lseek(file,tell(file)-sizeof(wall_t),SEEK_SET);
3937: }
3938: cls();
3939: offset=tell(file); } }
3940: cls();
3941: if(user_level<wall_level) {
3942: close(file);
3943: bputs("\r\n\1h\1rYou have insufficient access to write on the "
3944: "wall.\r\n");
3945: pause();
3946: break; }
3947: if(aborted || noyes("Write on the Wall")) {
3948: close(file);
3949: break; }
3950: if(!useron.number) {
3951: bputs("\r\n\1h\1rYou must create a profile first.\r\n");
3952: close(file);
3953: break; }
3954: if(!cdt_warning(wall_cdt)) {
3955: close(file);
3956: break; }
3957: memset(&wall,0,sizeof(wall_t));
3958: strcpy(wall.name,useron.name);
3959: strcpy(wall.system,system_name);
3960: wall.written=wall.imported=time(NULL);
3961: bputs("\1l\1n\1hWriting on the Wall:\r\n\r\n");
3962: for(i=0;i<5 && !aborted;i++) {
3963: bprintf("\1n\1h\1%c%u of 5: \1n\1%c"
3964: ,useron.sex=='F'?'m':'g',i+1,useron.sex=='F'?'m':'g');
3965: if(!getstr(wall.text[i],70,i==4 ? K_MSG:K_MSG|K_WRAP))
3966: break;
3967: if(trash(wall.text[i])) {
3968: bprintf("\r\n\1r\1hSorry, you can't use that text."
3969: "\r\n\r\n");
3970: i--;
3971: continue; } }
3972: if(!i || aborted || !yesno("\r\nSave")) {
3973: close(file);
3974: break; }
3975: lseek(file,0L,SEEK_END);
3976: write(file,&wall,sizeof(wall_t));
3977: close(file);
3978: adjust_cdt(wall_cdt);
3979: if(notify_user && notify_user!=user_number) {
3980: sprintf(str,"\1n\1hSMM: \1y%s\1m wrote on the Match Maker "
3981: "Wall\r\n",user_name);
3982: if(node_dir[0])
3983: putsmsg(notify_user,str);
3984: else
3985: puttgram(notify_user,str); }
3986: break;
3987: case 'Q':
3988: return; } }
3989: }
3990:
3991: /* End of SMM.C */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.