Annotation of sbbs/sbbs2/misc.c, revision 1.1

1.1     ! root        1: #line 1 "MISC.C"
        !             2: 
        !             3: /* Developed 1990-1997 by Rob Swindell; PO Box 501, Yorba Linda, CA 92885 */
        !             4: 
        !             5: /***************************************************************************/
        !             6: /* Miscellaneous functions that are useful many places throughout the code */
        !             7: /***************************************************************************/
        !             8: 
        !             9: #include "sbbs.h"
        !            10: #include "crc32.h"
        !            11: 
        !            12: #ifdef __WIN32__
        !            13: #include <windows.h>   // Required for kbd_state(), beep(), and mswait()
        !            14: #endif
        !            15: 
        !            16: /****************************************************************************/
        !            17: /* Returns the number of characters in 'str' not counting ctrl-ax codes                */
        !            18: /* or the null terminator                                                                                                      */
        !            19: /****************************************************************************/
        !            20: int bstrlen(char *str)
        !            21: {
        !            22:        int i=0;
        !            23: 
        !            24: while(*str) {
        !            25:        if(*str==1) /* ctrl-a */
        !            26:                str++;
        !            27:        else
        !            28:                i++;
        !            29:        if(!(*str)) break;
        !            30:        str++; }
        !            31: return(i);
        !            32: }
        !            33: 
        !            34: void strip_ctrl(char *str)
        !            35: {
        !            36:        char tmp[1024];
        !            37:        int i,j,k;
        !            38: 
        !            39: k=strlen(str);
        !            40: for(i=j=0;i<k;i++)
        !            41:        if(str[i]==1)  /* Ctrl-a */
        !            42:         i++;
        !            43:        else if(j && str[i]<=SP && tmp[j-1]==SP)
        !            44:                continue;
        !            45:        else if(i && !isalnum(str[i]) && str[i]==str[i-1])
        !            46:                continue;
        !            47:        else if((uchar)str[i]>=SP)
        !            48:                tmp[j++]=str[i];
        !            49:        else if(str[i]==TAB || (str[i]==CR && str[i+1]==LF))
        !            50:                tmp[j++]=SP;
        !            51: tmp[j]=0;
        !            52: strcpy(str,tmp);
        !            53: }
        !            54: 
        !            55: void strip_exascii(char *str)
        !            56: {
        !            57:        char tmp[1024];
        !            58:        int i,j,k;
        !            59: 
        !            60: k=strlen(str);
        !            61: for(i=j=0;i<k;i++)
        !            62:        if(!(str[i]&0x80))
        !            63:                tmp[j++]=str[i];
        !            64: tmp[j]=0;
        !            65: strcpy(str,tmp);
        !            66: }
        !            67: 
        !            68: /****************************************************************************/
        !            69: /* Returns in 'string' a character representation of the number in l with   */
        !            70: /* commas.                                                                                                                                     */
        !            71: /****************************************************************************/
        !            72: char *ultoac(ulong l, char *string)
        !            73: {
        !            74:        char str[256];
        !            75:        char i,j,k;
        !            76: 
        !            77: ultoa(l,str,10);
        !            78: i=strlen(str)-1;
        !            79: j=i/3+1+i;
        !            80: string[j--]=0;
        !            81: for(k=1;i>-1;k++) {
        !            82:        string[j--]=str[i--];
        !            83:        if(j>0 && !(k%3))
        !            84:                string[j--]=','; }
        !            85: return(string);
        !            86: }
        !            87: 
        !            88: /****************************************************************************/
        !            89: /* Network open function. Opens all files DENYALL and retries LOOP_NOPEN    */
        !            90: /* number of times if the attempted file is already open or denying access  */
        !            91: /* for some other reason.      All files are opened in BINARY mode.                    */
        !            92: /****************************************************************************/
        !            93: int nopen(char *str, int access)
        !            94: {
        !            95:        char logstr[256];
        !            96:        int file,share,count=0;
        !            97: 
        !            98: if(access&O_DENYNONE) {
        !            99:        share=SH_DENYNO;
        !           100:        access&=~O_DENYNONE; }
        !           101: else if(access==O_RDONLY) share=SH_DENYWR;
        !           102: else share=SH_DENYRW;
        !           103: while(((file=sopen(str,O_BINARY|access,share,S_IWRITE))==-1)
        !           104:        && errno==EACCES && count++<LOOP_NOPEN)
        !           105:        if(count>10)
        !           106:                mswait(55);
        !           107: if(count>(LOOP_NOPEN/2) && count<=LOOP_NOPEN) {
        !           108:        sprintf(logstr,"NOPEN COLLISION - File: %s Count: %d"
        !           109:                ,str,count);
        !           110:        logline("!!",logstr); }
        !           111: if(file==-1 && errno==EACCES)
        !           112:        bputs("\7\r\nNOPEN: ACCESS DENIED\r\n\7");
        !           113: return(file);
        !           114: }
        !           115: 
        !           116: /****************************************************************************/
        !           117: /* This function performs an nopen, but returns a file stream with a buffer */
        !           118: /* allocated.                                                                                                                          */
        !           119: /****************************************************************************/
        !           120: FILE *fnopen(int *file, char *str, int access)
        !           121: {
        !           122:        char mode[128];
        !           123:        FILE *stream;
        !           124: 
        !           125: if(((*file)=nopen(str,access))==-1)
        !           126:        return(NULL);
        !           127: 
        !           128: if(access&O_APPEND) {
        !           129:        if(access&O_RDONLY)
        !           130:                strcpy(mode,"a+");
        !           131:        else
        !           132:                strcpy(mode,"a"); }
        !           133: else {
        !           134:        if(access&O_WRONLY)
        !           135:                strcpy(mode,"r+");
        !           136:        else
        !           137:                strcpy(mode,"r"); }
        !           138: stream=fdopen((*file),mode);
        !           139: if(stream==NULL) {
        !           140:        close(*file);
        !           141:        errormsg(WHERE,ERR_FDOPEN,str,access);
        !           142:        return(NULL); }
        !           143: setvbuf(stream,NULL,_IOFBF,2*1024);
        !           144: return(stream);
        !           145: }
        !           146: 
        !           147: #ifndef __FLAT__
        !           148: /****************************************************************************/
        !           149: /* This function reads files that are potentially larger than 32k.             */
        !           150: /* Up to one megabyte of data can be read with each call.                   */
        !           151: /****************************************************************************/
        !           152: long lread(int file, char huge *buf,long bytes)
        !           153: {
        !           154:        long count;
        !           155: 
        !           156: for(count=bytes;count>32767;count-=32767,buf+=32767)
        !           157:        if(read(file,(char *)buf,32767)!=32767)
        !           158:                return(-1L);
        !           159: if(read(file,(char *)buf,(int)count)!=count)
        !           160:        return(-1L);
        !           161: return(bytes);
        !           162: }
        !           163: 
        !           164: long lfread(char huge *buf, long bytes, FILE *fp)
        !           165: {
        !           166:        long count;
        !           167: 
        !           168: for(count=bytes;count>0x7fff;count-=0x7fff,buf+=0x7fff)
        !           169:        if(fread((char *)buf,1,0x7fff,fp)!=0x7fff)
        !           170:                return(0);
        !           171: if(fread((char *)buf,1,(int)count,fp)!=count)
        !           172:        return(0);
        !           173: return(bytes);
        !           174: }
        !           175: 
        !           176: /****************************************************************************/
        !           177: /* This function writes files that are potentially larger than 32767 bytes  */
        !           178: /* Up to one megabytes of data can be written with each call.                          */
        !           179: /****************************************************************************/
        !           180: long lwrite(int file, char huge *buf, long bytes)
        !           181: {
        !           182: 
        !           183:        long count;
        !           184: 
        !           185: for(count=bytes;count>32767;count-=32767,buf+=32767)
        !           186:        if(write(file,(char *)buf,32767)!=32767)
        !           187:                return(-1L);
        !           188: if(write(file,(char *)buf,(int)count)!=count)
        !           189:        return(-1L);
        !           190: return(bytes);
        !           191: }
        !           192: #endif
        !           193: 
        !           194: /****************************************************************************/
        !           195: /* Truncates white-space chars off end of 'str' and terminates at first tab */
        !           196: /****************************************************************************/
        !           197: void truncsp(char *str)
        !           198: {
        !           199:        uint c;
        !           200: 
        !           201: str[strcspn(str,"\t")]=0;
        !           202: c=strlen(str);
        !           203: while(c && (uchar)str[c-1]<=SP) c--;
        !           204: str[c]=0;
        !           205: }
        !           206: 
        !           207: /****************************************************************************/
        !           208: /* Puts a backslash on path strings                                                                            */
        !           209: /****************************************************************************/
        !           210: void backslash(char *str)
        !           211: {
        !           212:     int i;
        !           213: 
        !           214: i=strlen(str);
        !           215: if(i && str[i-1]!='\\') {
        !           216:     str[i]='\\'; str[i+1]=0; }
        !           217: }
        !           218: 
        !           219: /****************************************************************************/
        !           220: /* Puts a backslash on path strings if not just a drive letter and colon       */
        !           221: /****************************************************************************/
        !           222: void backslashcolon(char *str)
        !           223: {
        !           224:     int i;
        !           225: 
        !           226: i=strlen(str);
        !           227: if(i && str[i-1]!='\\' && str[i-1]!=':') {
        !           228:     str[i]='\\'; str[i+1]=0; }
        !           229: }
        !           230: 
        !           231: /****************************************************************************/
        !           232: /* Updates 16-bit "rcrc" with character 'ch'                                */
        !           233: /****************************************************************************/
        !           234: void ucrc16(uchar ch, ushort *rcrc) {
        !           235:        ushort i, cy;
        !           236:     uchar nch=ch;
        !           237:  
        !           238: for (i=0; i<8; i++) {
        !           239:     cy=*rcrc & 0x8000;
        !           240:     *rcrc<<=1;
        !           241:     if (nch & 0x80) *rcrc |= 1;
        !           242:     nch<<=1;
        !           243:     if (cy) *rcrc ^= 0x1021; }
        !           244: }
        !           245: 
        !           246: /****************************************************************************/
        !           247: /* Returns CRC-16 of string (not including terminating NULL)                           */
        !           248: /****************************************************************************/
        !           249: ushort crc16(char *str)
        !           250: {
        !           251:        int     i=0;
        !           252:        ushort  crc=0;
        !           253: 
        !           254: ucrc16(0,&crc);
        !           255: while(str[i])
        !           256:        ucrc16(str[i++],&crc);
        !           257: ucrc16(0,&crc);
        !           258: ucrc16(0,&crc);
        !           259: return(crc);
        !           260: }
        !           261: 
        !           262: /****************************************************************************/
        !           263: /* Returns CRC-32 of string (not including terminating NULL)                           */
        !           264: /****************************************************************************/
        !           265: ulong crc32(char *buf, ulong len)
        !           266: {
        !           267:        ulong l,crc=0xffffffff;
        !           268: 
        !           269: for(l=0;l<len;l++)
        !           270:        crc=ucrc32(buf[l],crc);
        !           271: return(~crc);
        !           272: }
        !           273: 
        !           274: /****************************************************************************/
        !           275: /* Compares pointers to pointers to char. Used in conjuction with qsort()   */
        !           276: /****************************************************************************/
        !           277: int pstrcmp(char **str1, char **str2)
        !           278: {
        !           279: return(strcmp(*str1,*str2));
        !           280: }
        !           281: 
        !           282: /****************************************************************************/
        !           283: /* Returns the number of characters that are the same between str1 and str2 */
        !           284: /****************************************************************************/
        !           285: int strsame(char *str1, char *str2)
        !           286: {
        !           287:        int i,j=0;
        !           288: 
        !           289: for(i=0;i<strlen(str1);i++)
        !           290:        if(str1[i]==str2[i]) j++;
        !           291: return(j);
        !           292: }
        !           293: 
        !           294: #define MV_BUFLEN      4096
        !           295: 
        !           296: /****************************************************************************/
        !           297: /* Moves or copies a file from one dir to another                           */
        !           298: /* both 'src' and 'dest' must contain full path and filename                */
        !           299: /* returns 0 if successful, -1 if error                                     */
        !           300: /****************************************************************************/
        !           301: int mv(char *src, char *dest, char copy)
        !           302: {
        !           303:        char str[256],*buf,atr=curatr;
        !           304:        int  ind,outd;
        !           305:        long length,chunk=MV_BUFLEN,l;
        !           306:        struct ftime ftime;
        !           307:        FILE *inp,*outp;
        !           308: 
        !           309: if(!stricmp(src,dest))  /* source and destination are the same! */
        !           310:        return(0);
        !           311: if(!fexist(src)) {
        !           312:        bprintf("\r\n\7MV ERROR: Source doesn't exist\r\n'%s'\r\n"
        !           313:                ,src);
        !           314:        return(-1); }
        !           315: if(!copy && fexist(dest)) {
        !           316:        bprintf("\r\n\7MV ERROR: Destination already exists\r\n'%s'\r\n"
        !           317:                ,dest);
        !           318:        return(-1); }
        !           319: if(!copy && ((src[1]!=':' && dest[1]!=':')
        !           320:        || (src[1]==':' && dest[1]==':' && toupper(src[0])==toupper(dest[0])))) {
        !           321:        if(rename(src,dest)) {                                          /* same drive, so move */
        !           322:                bprintf("\r\nMV ERROR: Error renaming '%s'"
        !           323:                                "\r\n                      to '%s'\r\n\7",src,dest);
        !           324:                return(-1); }
        !           325:        return(0); }
        !           326: attr(WHITE);
        !           327: if((ind=nopen(src,O_RDONLY))==-1) {
        !           328:        errormsg(WHERE,ERR_OPEN,src,O_RDONLY);
        !           329:        return(-1); }
        !           330: if((inp=fdopen(ind,"rb"))==NULL) {
        !           331:        close(ind);
        !           332:        errormsg(WHERE,ERR_FDOPEN,str,O_RDONLY);
        !           333:        return(-1); }
        !           334: setvbuf(inp,NULL,_IOFBF,32*1024);
        !           335: if((outd=nopen(dest,O_WRONLY|O_CREAT|O_TRUNC))==-1) {
        !           336:        fclose(inp);
        !           337:        errormsg(WHERE,ERR_OPEN,dest,O_WRONLY|O_CREAT|O_TRUNC);
        !           338:        return(-1); }
        !           339: if((outp=fdopen(outd,"wb"))==NULL) {
        !           340:        close(outd);
        !           341:        fclose(inp);
        !           342:        errormsg(WHERE,ERR_FDOPEN,dest,O_WRONLY|O_CREAT|O_TRUNC);
        !           343:        return(-1); }
        !           344: setvbuf(outp,NULL,_IOFBF,8*1024);
        !           345: length=filelength(ind);
        !           346: if(!length) {
        !           347:        fclose(inp);
        !           348:        fclose(outp);
        !           349:        errormsg(WHERE,ERR_LEN,src,0);
        !           350:        return(-1); }
        !           351: if((buf=(char *)MALLOC(MV_BUFLEN))==NULL) {
        !           352:        fclose(inp);
        !           353:        fclose(outp);
        !           354:        errormsg(WHERE,ERR_ALLOC,nulstr,MV_BUFLEN);
        !           355:        return(-1); }
        !           356: l=0L;
        !           357: while(l<length) {
        !           358:        bprintf("%2lu%%",l ? (long)(100.0/((float)length/l)) : 0L);
        !           359:        if(l+chunk>length)
        !           360:                chunk=length-l;
        !           361:        if(fread(buf,1,chunk,inp)!=chunk) {
        !           362:                FREE(buf);
        !           363:                fclose(inp);
        !           364:                fclose(outp);
        !           365:                errormsg(WHERE,ERR_READ,src,chunk);
        !           366:                return(-1); }
        !           367:        if(fwrite(buf,1,chunk,outp)!=chunk) {
        !           368:                FREE(buf);
        !           369:                fclose(inp);
        !           370:                fclose(outp);
        !           371:                errormsg(WHERE,ERR_WRITE,dest,chunk);
        !           372:                return(-1); }
        !           373:        l+=chunk;
        !           374:        bputs("\b\b\b"); }
        !           375: bputs("   \b\b\b");  /* erase it */
        !           376: attr(atr);
        !           377: getftime(ind,&ftime);
        !           378: setftime(outd,&ftime);
        !           379: FREE(buf);
        !           380: fclose(inp);
        !           381: fclose(outp);
        !           382: if(!copy && remove(src)) {
        !           383:        errormsg(WHERE,ERR_REMOVE,src,0);
        !           384:        return(-1); }
        !           385: return(0);
        !           386: }
        !           387: 
        !           388: /****************************************************************************/
        !           389: /* Prompts user for System Password. Returns 1 if user entered correct PW      */
        !           390: /****************************************************************************/
        !           391: char chksyspass(int local)
        !           392: {
        !           393:        static  int inside;
        !           394:        char    str[256],str2[256],x,y,atr;
        !           395:        int     orgcon=console;
        !           396: 
        !           397: if(inside) return(0);
        !           398: if(online==ON_REMOTE && !(sys_misc&SM_R_SYSOP))
        !           399:        return(0);
        !           400: if(online==ON_LOCAL) {
        !           401:        if(!(sys_misc&SM_L_SYSOP))
        !           402:                return(0);
        !           403:        if(!(node_misc&NM_SYSPW) && !(sys_misc&SM_REQ_PW))
        !           404:                return(1); }
        !           405: if(local) {
        !           406:        x=lclwx();
        !           407:        y=lclwy();
        !           408:        atr=lclatr(LIGHTGRAY<<4);
        !           409:        STATUSLINE;
        !           410:        lclxy(1,node_scrnlen);
        !           411:        lputc(CLREOL);
        !           412:        lputs("  System Password: "); }
        !           413: else
        !           414:        bputs("SY: ");
        !           415: console&=~(CON_R_ECHO|CON_L_ECHO);
        !           416: inside=1;
        !           417: getstr(str,40,K_UPPER);
        !           418: if(local) {
        !           419:        TEXTWINDOW;
        !           420:        lclatr(atr);
        !           421:        lclxy(x,y);
        !           422:        statusline(); }
        !           423: inside=0;
        !           424: console=orgcon;
        !           425: if(!local)
        !           426:        CRLF;
        !           427: if(strcmp(sys_pass,str)) {
        !           428:        sprintf(str2,"%s #%u System password attempt: '%s'"
        !           429:                ,useron.alias,useron.number,str);
        !           430:        logline("S!",str2);
        !           431:        return(0); }
        !           432: return(1);
        !           433: }
        !           434: 
        !           435: /****************************************************************************/
        !           436: /* Converts when_t.zone into ASCII format                                   */
        !           437: /****************************************************************************/
        !           438: char *zonestr(short zone)
        !           439: {
        !           440:     static char str[32];
        !           441: 
        !           442: switch((ushort)zone) {
        !           443:     case 0:     return("UT");
        !           444:     case AST:   return("AST");
        !           445:     case EST:   return("EST");
        !           446:     case CST:   return("CST");
        !           447:     case MST:   return("MST");
        !           448:     case PST:   return("PST");
        !           449:     case YST:   return("YST");
        !           450:     case HST:   return("HST");
        !           451:     case BST:   return("BST");
        !           452:     case ADT:   return("ADT");
        !           453:     case EDT:   return("EDT");
        !           454:     case CDT:   return("CDT");
        !           455:     case MDT:   return("MDT");
        !           456:     case PDT:   return("PDT");
        !           457:     case YDT:   return("YDT");
        !           458:     case HDT:   return("HDT");
        !           459:     case BDT:   return("BDT");
        !           460:     case MID:   return("MID");
        !           461:     case VAN:   return("VAN");
        !           462:     case EDM:   return("EDM");
        !           463:     case WIN:   return("WIN");
        !           464:     case BOG:   return("BOG");
        !           465:     case CAR:   return("CAR");
        !           466:     case RIO:   return("RIO");
        !           467:     case FER:   return("FER");
        !           468:     case AZO:   return("AZO");
        !           469:     case LON:   return("LON");
        !           470:     case BER:   return("BER");
        !           471:     case ATH:   return("ATH");
        !           472:     case MOS:   return("MOS");
        !           473:     case DUB:   return("DUB");
        !           474:     case KAB:   return("KAB");
        !           475:     case KAR:   return("KAR");
        !           476:     case BOM:   return("BOM");
        !           477:     case KAT:   return("KAT");
        !           478:     case DHA:   return("DHA");
        !           479:     case BAN:   return("BAN");
        !           480:     case HON:   return("HON");
        !           481:     case TOK:   return("TOK");
        !           482:     case SYD:   return("SYD");
        !           483:     case NOU:   return("NOU");
        !           484:     case WEL:   return("WEL");
        !           485:     }
        !           486: 
        !           487: sprintf(str,"%02d:%02u",zone/60,zone<0 ? (-zone)%60 : zone%60);
        !           488: return(str);
        !           489: }
        !           490: 
        !           491: /****************************************************************************/
        !           492: /* Waits so many seconds. Call with 2 or greater.                                                      */
        !           493: /****************************************************************************/
        !           494: void secwait(int sec)
        !           495: {
        !           496:        time_t start;
        !           497: 
        !           498: start=time(NULL);
        !           499: while(time(NULL)-start<sec)
        !           500:        mswait(1);
        !           501: }
        !           502: 
        !           503: /****************************************************************************/
        !           504: /* Converts a date string in format MM/DD/YY into unix time format                     */
        !           505: /****************************************************************************/
        !           506: time_t dstrtounix(char *str)
        !           507: {
        !           508: 
        !           509: if(!strncmp(str,"00/00/00",8))
        !           510:        return(0);
        !           511: curtime.ti_hour=curtime.ti_min=curtime.ti_sec=0;
        !           512: if(str[6]<'7')
        !           513:        date.da_year=2000+((str[6]&0xf)*10)+(str[7]&0xf);
        !           514: else
        !           515:        date.da_year=1900+((str[6]&0xf)*10)+(str[7]&0xf);
        !           516: if(sys_misc&SM_EURODATE) {
        !           517:        date.da_mon=((str[3]&0xf)*10)+(str[4]&0xf);
        !           518:        date.da_day=((str[0]&0xf)*10)+(str[1]&0xf); }
        !           519: else {
        !           520:        date.da_mon=((str[0]&0xf)*10)+(str[1]&0xf);
        !           521:        date.da_day=((str[3]&0xf)*10)+(str[4]&0xf); }
        !           522: return(dostounix(&date,&curtime));
        !           523: }
        !           524: 
        !           525: /****************************************************************************/
        !           526: /* Converts unix time format (long - time_t) into a char str MM/DD/YY          */
        !           527: /****************************************************************************/
        !           528: char *unixtodstr(time_t unix, char *str)
        !           529: {
        !           530: 
        !           531: if(!unix)
        !           532:        strcpy(str,"00/00/00");
        !           533: else {
        !           534:        unixtodos(unix,&date,&curtime);
        !           535:        if((unsigned)date.da_mon>12) {    /* DOS leap year bug */
        !           536:                date.da_mon=1;
        !           537:                date.da_year++; }
        !           538:        if((unsigned)date.da_day>31)
        !           539:                date.da_day=1;
        !           540:        if(sys_misc&SM_EURODATE)
        !           541:                sprintf(str,"%02u/%02u/%02u",date.da_day,date.da_mon
        !           542:                        ,date.da_year>=2000 ? date.da_year-2000 : date.da_year-1900);
        !           543:        else
        !           544:                sprintf(str,"%02u/%02u/%02u",date.da_mon,date.da_day
        !           545:                        ,date.da_year>=2000 ? date.da_year-2000 : date.da_year-1900); }
        !           546: return(str);
        !           547: }
        !           548: 
        !           549: /****************************************************************************/
        !           550: /* Checks the disk drive for the existence of a file. Returns 1 if it       */
        !           551: /* exists, 0 if it doesn't.                                                 */
        !           552: /****************************************************************************/
        !           553: char fexist(char *filespec)
        !           554: {
        !           555:     struct ffblk f;
        !           556: 
        !           557: if(findfirst(filespec,&f,0 /*FA_RDONLY|FA_HIDDEN|FA_SYSTEM|FA_DIREC */)==0)
        !           558:     return(1);
        !           559: return(0);
        !           560: }
        !           561: 
        !           562: /****************************************************************************/
        !           563: /* Returns the length of the file in 'filespec'                             */
        !           564: /****************************************************************************/
        !           565: long flength(char *filespec)
        !           566: {
        !           567:        struct ffblk f;
        !           568: 
        !           569: if(findfirst(filespec,&f,0)==0)
        !           570:        return(f.ff_fsize);
        !           571: return(-1L);
        !           572: }
        !           573: 
        !           574: time_t ftimetounix(struct ftime ft)
        !           575: {
        !           576:        struct date da;
        !           577:        struct time ti;
        !           578: 
        !           579: ti.ti_min=ft.ft_min;
        !           580: ti.ti_hour=ft.ft_hour;
        !           581: ti.ti_hund=0;
        !           582: ti.ti_sec=ft.ft_tsec*2;
        !           583: da.da_year=1980+ft.ft_year;
        !           584: da.da_day=ft.ft_day;
        !           585: da.da_mon=ft.ft_month;
        !           586: return(dostounix(&da,&ti));
        !           587: }
        !           588: 
        !           589: struct ftime unixtoftime(time_t unix)
        !           590: {
        !           591:        struct date da;
        !           592:        struct time ti;
        !           593:        struct ftime ft;
        !           594: 
        !           595: unixtodos(unix,&da,&ti);
        !           596: ft.ft_min=ti.ti_min;
        !           597: ft.ft_hour=ti.ti_hour;
        !           598: ft.ft_tsec=ti.ti_sec/2;
        !           599: ft.ft_year=da.da_year-1980;
        !           600: ft.ft_day=da.da_day;
        !           601: ft.ft_month=da.da_mon;
        !           602: return(ft);
        !           603: }
        !           604: 
        !           605: /****************************************************************************/
        !           606: /* Returns the time/date of the file in 'filespec' in time_t (unix) format  */
        !           607: /****************************************************************************/
        !           608: long fdate(char *filespec)
        !           609: {
        !           610:     int file;
        !           611:     struct ftime f;
        !           612:        time_t t;
        !           613: 
        !           614: if((file=nopen(filespec,O_RDONLY))==-1)
        !           615:        return(0);
        !           616: getftime(file,&f);
        !           617: t=ftimetounix(f);
        !           618: close(file);
        !           619: return(t);
        !           620: }
        !           621: 
        !           622: long fdate_dir(char *filespec)
        !           623: {
        !           624:     struct ffblk f;
        !           625:     struct date fd;
        !           626:     struct time ft;
        !           627: 
        !           628: if(findfirst(filespec,&f,0/* FA_RDONLY|FA_HIDDEN|FA_SYSTEM|FA_DIREC */)==0) {
        !           629:        fd.da_day=f.ff_fdate&0x1f;
        !           630:        fd.da_mon=(f.ff_fdate>>5)&0xf;
        !           631:        fd.da_year=1980+((f.ff_fdate>>9)&0x7f);
        !           632:        ft.ti_hour=(f.ff_ftime>>11)&0x1f;
        !           633:        ft.ti_min=(f.ff_ftime>>5)&0x3f;
        !           634:        ft.ti_sec=(f.ff_ftime&0xf)*2;
        !           635:     return(dostounix(&fd,&ft)); }
        !           636: else return(0);
        !           637: }
        !           638: 
        !           639: 
        !           640: 
        !           641: /****************************************************************************/
        !           642: /* Returns the FidoNet address kept in str as ASCII.                        */
        !           643: /****************************************************************************/
        !           644: faddr_t atofaddr(char *str)
        !           645: {
        !           646:     char *p;
        !           647:     faddr_t addr;
        !           648: 
        !           649: addr.zone=addr.net=addr.node=addr.point=0;
        !           650: if((p=strchr(str,':'))!=NULL) {
        !           651:     addr.zone=atoi(str);
        !           652:     addr.net=atoi(p+1); }
        !           653: else {
        !           654:     if(total_faddrs)
        !           655:                addr.zone=faddr[0].zone;
        !           656:     else
        !           657:         addr.zone=1;
        !           658:     addr.net=atoi(str); }
        !           659: if(!addr.zone)              /* no such thing as zone 0 */
        !           660:     addr.zone=1;
        !           661: if((p=strchr(str,'/'))!=NULL)
        !           662:     addr.node=atoi(p+1);
        !           663: else {
        !           664:     if(total_faddrs)
        !           665:                addr.net=faddr[0].net;
        !           666:     else
        !           667:         addr.net=1;
        !           668:     addr.node=atoi(str); }
        !           669: if((p=strchr(str,'.'))!=NULL)
        !           670:     addr.point=atoi(p+1);
        !           671: return(addr);
        !           672: }
        !           673: 
        !           674: /****************************************************************************/
        !           675: /* Returns an ASCII string for FidoNet address 'addr'                       */
        !           676: /****************************************************************************/
        !           677: char *faddrtoa(faddr_t addr)
        !           678: {
        !           679:     static char str[25];
        !           680:     char point[25];
        !           681: 
        !           682: sprintf(str,"%u:%u/%u",addr.zone,addr.net,addr.node);
        !           683: if(addr.point) {
        !           684:     sprintf(point,".%u",addr.point);
        !           685:     strcat(str,point); }
        !           686: return(str);
        !           687: }
        !           688: 
        !           689: /****************************************************************************/
        !           690: /* Returns string for 2 digit hex+ numbers up to 575                                           */
        !           691: /****************************************************************************/
        !           692: char *hexplus(uint num, char *str)
        !           693: {
        !           694: sprintf(str,"%03x",num);
        !           695: str[0]=num/0x100 ? 'f'+(num/0x10)-0xf : str[1];
        !           696: str[1]=str[2];
        !           697: str[2]=0;
        !           698: return(str);
        !           699: }
        !           700: 
        !           701: uint hptoi(char *str)
        !           702: {
        !           703:        char tmp[128];
        !           704:        uint i;
        !           705: 
        !           706: if(!str[1] || toupper(str[0])<='F')
        !           707:        return(ahtoul(str));
        !           708: strcpy(tmp,str);
        !           709: tmp[0]='F';
        !           710: i=ahtoul(tmp)+((toupper(str[0])-'F')*0x10);
        !           711: return(i);
        !           712: }
        !           713: 
        !           714: #ifndef __FLAT__
        !           715: 
        !           716: void beep(int freq, int dur)
        !           717: {
        !           718: sound(freq);
        !           719: mswait(dur);
        !           720: nosound();
        !           721: }
        !           722: 
        !           723: int kbd_state(void)
        !           724: {
        !           725: return(peekb(0,0x417));         /* Check scroll lock */
        !           726: }
        !           727: 
        !           728: #elif defined(__WIN32__)
        !           729: 
        !           730: void beep(int freq, int dur)
        !           731: {
        !           732: Beep(freq,dur);                                // Requires WINDOWS.H
        !           733: }
        !           734: 
        !           735: void mswait(int ms)
        !           736: {
        !           737: Sleep(ms);                                             // Requires WINDOWS.H
        !           738: }
        !           739: 
        !           740: #endif
        !           741: 
        !           742: #ifdef __OS2__
        !           743: 
        !           744: int kbd_state(void)
        !           745: {
        !           746:        KBDINFO info;
        !           747: 
        !           748: KbdGetStatus(&info,0);
        !           749: return(info.fsState);
        !           750: }
        !           751: 
        !           752: void mswait(int msec)
        !           753: {
        !           754: DosSleep(msec ? msec : 1);
        !           755: }
        !           756: 
        !           757: #elif defined(__WIN32__)
        !           758: 
        !           759: #define KBDSTF_RIGHTSHIFT                              0x0001
        !           760: #define KBDSTF_LEFTSHIFT                               0x0002
        !           761: #define KBDSTF_CONTROL                                 0x0004
        !           762: #define KBDSTF_ALT                                             0x0008
        !           763: #define KBDSTF_SCROLLLOCK_ON                   0x0010
        !           764: #define KBDSTF_NUMLOCK_ON                              0x0020
        !           765: #define KBDSTF_CAPSLOCK_ON                             0x0040
        !           766: #define KBDSTF_INSERT_ON                               0x0080
        !           767: #define KBDSTF_LEFTCONTROL                             0x0100
        !           768: #define KBDSTF_LEFTALT                                 0x0200
        !           769: #define KBDSTF_RIGHTCONTROL                    0x0400
        !           770: #define KBDSTF_RIGHTALT                                0x0800
        !           771: #define KBDSTF_SCROLLLOCK                              0x1000
        !           772: #define KBDSTF_NUMLOCK                                 0x2000
        !           773: #define KBDSTF_CAPSLOCK                                0x4000
        !           774: #define KBDSTF_SYSREQ                                  0x8000
        !           775: 
        !           776: int kbd_state(void)
        !           777: {
        !           778:        int i=0;
        !           779:        ulong l;
        !           780:        INPUT_RECORD rec;
        !           781: 
        !           782: PeekConsoleInput(stdin,&rec,1,&l);
        !           783: if(rec.EventType==KEY_EVENT)
        !           784:        l=rec.Event.KeyEvent.dwControlKeyState;
        !           785: else if(rec.EventType==MOUSE_EVENT)
        !           786:        l=rec.Event.MouseEvent.dwControlKeyState;
        !           787: else
        !           788:        return(0);
        !           789: 
        !           790: /* Translate Win32 key state to IBM key state */
        !           791: 
        !           792: if(l&RIGHT_ALT_PRESSED)
        !           793:        i|=KBDSTF_RIGHTALT;
        !           794: if(l&LEFT_ALT_PRESSED)
        !           795:        i|=KBDSTF_LEFTALT;
        !           796: if(l&RIGHT_CTRL_PRESSED)
        !           797:        i|=KBDSTF_RIGHTCONTROL;
        !           798: if(l&LEFT_CTRL_PRESSED)
        !           799:        i|=KBDSTF_LEFTCONTROL;
        !           800: if(l&CAPSLOCK_ON)
        !           801:        i|=KBDSTF_CAPSLOCK;
        !           802: if(l&NUMLOCK_ON)
        !           803:        i|=KBDSTF_NUMLOCK;
        !           804: if(l&SCROLLLOCK_ON)
        !           805:        i|=KBDSTF_SCROLLLOCK;
        !           806: if(l&SHIFT_PRESSED)
        !           807:        i|=KBDSTF_LEFTSHIFT;
        !           808: 
        !           809: return(i);
        !           810: }
        !           811: 
        !           812: 
        !           813: 
        !           814: #endif
        !           815: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.