home *** CD-ROM | disk | FTP | other *** search
- /*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*/
- /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
- /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
- /* * * */
- /* * strlib.c library of string-manipulating functions * */
- /* * * */
- /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
- /* * Marc A. Murison * * * * * * * * * * * * * * * * * * * * * * * * * * * */
- /*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*/
-
- /*
- * This software may be freely distributed under the following conditions:
- * 1. It is distributed in its current form, without alterations.
- * 2. No monetary profit is made, under any circumstances.
- *
- * Marc A. Murison
- * Smithsonian Astrophysical Observatory
- * 60 Garden Street, MS 63
- * Cambridge, MA 02138
- *
- * (617) 495-7079 murison@cfacx2.harvard.edu
- */
-
-
-
- #define global extern
- #define STRLIB_C
- #define KEY_CODES
- #include "strlib.h"
-
-
-
-
- #ifdef __TURBOC__
- /*-----------------------------------------------------------------------------
- * text buffer browse utility
- *
- * returns 0 if unable to allocate enough memory for storing current text
- * screen; 1 otherwise
- *---------------------------------------------------------------------------*/
- Boolean browse( char *text, char *title )
- {
- unsigned size;
- int i, top_line, bot_line, nlines;
- Key_Code key;
- Boolean start_text, end_text, extended;
- char *old_screen, *lp_top, *lp_bot, *end_of_text;
- char *info_bar = "* Quit: Q Esc * "
- "Up: Enter Up PgUp Home * "
- "Down: Space Dn PgDn End *";
- enum colors text_fg, text_bkg, title_fg, title_bkg,
- info_fg, info_bkg;
- struct text_info current;
-
-
- /* assign colors */
- text_fg = BLACK;
- text_bkg = LIGHTGRAY;
- title_fg = WHITE;
- title_bkg = RED;
- info_fg = WHITE;
- info_bkg = RED;
-
-
- /* save current text screen */
- gettextinfo( ¤t );
- size = ((current.screenheight*current.screenwidth*2) / 1000) * 1024;
- old_screen = cvector( 0, size-1 );
- if( old_screen == NULL ) return FALSE;
- gettext( 1, 1, current.screenwidth, current.screenheight, old_screen );
-
-
- /* find the end of the input text (for use in paging down) */
- end_of_text = text;
- while( *end_of_text ) ++end_of_text;
-
-
- /* write the title bar */
- _setcursortype( _NOCURSOR );
- window( 1, 1, current.screenwidth, 1 );
- textcolor( title_fg );
- textbackground( title_bkg );
- clrscr();
- i = 1 + (current.screenwidth - strlen( title )) / 2;
- gotoxy( i, 1 );
- while( *title ) { putchar(*title); ++title; }
-
-
- /* write the info bar */
- window( 1, current.screenheight, current.screenwidth, current.screenheight);
- textcolor( info_fg );
- textbackground( info_bkg );
- clrscr();
- i = 1 + (current.screenwidth - strlen( info_bar )) / 2;
- gotoxy( i, 1 );
- while( *info_bar ) { putchar(*info_bar); ++info_bar; }
-
-
- /* side borders */
- window( 1, 2, 1, current.screenheight-1 );
- clrscr();
- window( current.screenwidth, 2,
- current.screenwidth, current.screenheight-1 );
- clrscr();
-
-
- /* define new window */
- window( 2, 2, current.screenwidth-1, current.screenheight-1 );
- textcolor( text_fg );
- textbackground( text_bkg );
- clrscr();
- gotoxy( 1, 1 );
- top_line = 1;
- bot_line = current.screenheight - 2;
- nlines = bot_line - top_line + 1;
-
-
- /* print the first screenful of text */
- lp_top = text;
- lp_bot = text;
- for( i=0; i < nlines; i++ ) {
- gotoxy( 1, top_line+i );
- cprint_line( OFF, &lp_bot );
- }
- start_text = TRUE;
- if( *lp_bot == NULL )
- end_text = TRUE;
- else
- end_text = FALSE;
-
-
- /* interpret keystrokes */
- extended = ON;
- key = KEY_CR; /* dummy start value */
- while( BROWSE_KEY( extended, key ) ) {
- i = getch();
- if( i == 0 ) {
- extended = ON;
- key = (Key_Code) getch();
- } else {
- extended = OFF;
- key = (Key_Code) i;
- }
-
- /* scroll window up */
- if( (key == KEY_UP && extended) || key == KEY_CR ) {
- if( !start_text ) {
- /* insert a blank line at the top */
- gotoxy( 1, top_line );
- insline();
- clreol();
-
- /* point to previous text line */
- if( !prev_line( &lp_top, text ) ) start_text = TRUE;
-
- /* print the previous text line */
- cprint_line( OFF, &lp_top );
- prev_line( &lp_top, text ); /* but don't advance */
- end_text = FALSE;
-
- /* update bottom line pointer */
- prev_line( &lp_bot, text );
- }
-
- /* scroll window down */
- } else if( (key == KEY_DN && extended) || key == KEY_SP ) {
- if( !end_text ) {
- /* delete the top line and scroll window contents up */
- gotoxy( 1, top_line );
- delline();
-
- /* print next line of text */
- gotoxy( 1, bot_line );
- clreol();
- cprint_line( OFF, &lp_bot );
- if( *lp_bot == NULL ) end_text = TRUE;
- start_text = FALSE;
-
- /* update top line pointer */
- next_line( &lp_top );
- }
-
- /* page window up */
- } else if( key == KEY_PGUP && extended ) {
- if( !start_text ) {
- clrscr();
- for( i=0; i < nlines; i++ ) prev_line( &lp_top, text );
- if( lp_top <= text ) {
- lp_top = text;
- start_text = TRUE;
- } else
- start_text = FALSE;
- lp_bot = lp_top;
- for( i=0; i < nlines; i++ ) {
- gotoxy( 1, top_line+i );
- cprint_line( OFF, &lp_bot );
- }
- if( lp_bot >= end_of_text )
- end_text = TRUE;
- else
- end_text = FALSE;
- }
-
- /* page window down */
- } else if( key == KEY_PGDN && extended ) {
- if( !end_text ) {
- clrscr();
- for( i=0; i < nlines; i++ ) next_line( &lp_bot );
- if( lp_bot >= end_of_text ) {
- lp_top = end_of_text;
- for( i=0; i < nlines; i++ ) prev_line( &lp_top, text );
- end_text = TRUE;
- } else
- for( i=0; i < nlines; i++ ) next_line( &lp_top );
- start_text = FALSE;
- lp_bot = lp_top;
- for( i=0; i < nlines; i++ ) {
- gotoxy( 1, top_line+i );
- cprint_line( OFF, &lp_bot );
- }
- }
-
- /* home */
- } else if( key == KEY_HOME && extended ) {
- if( !start_text ) {
- clrscr();
- lp_top = text;
- lp_bot = text;
- for( i=0; i < nlines; i++ ) {
- gotoxy( 1, top_line+i );
- cprint_line( OFF, &lp_bot );
- }
- start_text = TRUE;
- if( *lp_bot == NULL )
- end_text = TRUE;
- else
- end_text = FALSE;
- }
-
- /* end */
- } else if( key == KEY_END && extended ) {
- if( !end_text ) {
- clrscr();
- lp_top = end_of_text;
- for( i=0; i < nlines; i++ ) prev_line( &lp_top, text );
- if( lp_top <= text ) {
- lp_top = text;
- start_text = TRUE;
- }
- else
- start_text = FALSE;
- lp_bot = lp_top;
- for( i=0; i < nlines; i++ ) {
- gotoxy( 1, top_line+i );
- cprint_line( OFF, &lp_bot );
- }
- end_text = TRUE;
- }
- }
- }
-
-
- /* restore old screen */
- window( 1, 1, current.screenwidth, current.screenheight );
- puttext( 1, 1, current.screenwidth, current.screenheight, old_screen );
- gotoxy( current.curx, current.cury );
- _setcursortype( _NORMALCURSOR );
-
- return TRUE;
- }
- #endif
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean next_line( char **bp )
- *
- * advance buffer pointer to character after next newline character
- *
- * contents of bp updated to new position in buffer, which is the first
- * character after the next newline
- *
- * returns: 1 successful
- * 0 NULL encountered
- *---------------------------------------------------------------------------*/
- Boolean next_line( char **bp )
- {
- /* go to next newline character */
- if( !end_line( bp ) ) return FALSE;
-
- /* next character after that */
- ++(*bp);
- if( **bp == NULL )
- return FALSE;
- else
- return TRUE;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean prev_line( char **bp, char *buffer )
- *
- * move buffer pointer to character before previous newline character
- *
- * contents of bp updated to new position in buffer, which is the first
- * character after the newline beginning the previous line
- *
- * returns: 1 successful
- * 0 beginning of buffer encountered
- *---------------------------------------------------------------------------*/
- Boolean prev_line( char **bp, char *buffer )
- {
-
- /*
- * special case:
- * if we're sitting on a newline, and the previous 2 chars are newlines,
- * move to the middle newline
- */
- if( **bp == NEWLINE && *(*bp-1) == NEWLINE && *(*bp-2) == NEWLINE ) {
- --(*bp);
- if( *bp <= buffer ) { *bp = buffer; return FALSE; }
- return TRUE;
- }
-
-
- /*
- * special case:
- * if we're sitting on a newline, and the preceding char is a newline but the
- * next preceding one isn't, move to before the newlines and then to the
- * beginning of that line
- */
- if( **bp == NEWLINE && *(*bp-1) == NEWLINE ) {
- *bp -= 2;
- if( *bp <= buffer ) { *bp = buffer; return FALSE; }
- if( !beg_line( bp, buffer ) ) {
- if( **bp == NEWLINE ) { /* 1st char of buffer = '\n' */
- ++(*bp);
- return TRUE;
- } else
- return FALSE;
- }
- ++(*bp);
- return TRUE;
- }
-
-
- /*
- * normal case:
- */
-
- /* move to beginning of current line */
- if( !beg_line( bp, buffer ) ) return FALSE;
-
- /* move to beginning of previous line (1st char after newline) */
- --(*bp);
- if( *bp < buffer ) { *bp = buffer; return FALSE; }
- if( !beg_line( bp, buffer ) ) {
- if( **bp == NEWLINE ) { /* 1st char of buffer = '\n' */
- ++(*bp);
- return TRUE;
- } else
- return FALSE;
- }
- ++(*bp);
- return TRUE;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean beg_line( char **bp, char *buffer )
- *
- * move buffer pointer to preceding newline character
- *
- * contents of bp updated to new position in buffer, which is the
- * the newline beginning the current line
- *
- * returns: 1 successful
- * 0 beginning of buffer encountered
- *---------------------------------------------------------------------------*/
- Boolean beg_line( char **bp, char *buffer )
- {
- char *p;
-
- p = *bp;
- if( p <= buffer ) { *bp = buffer; return FALSE; }
- while( *p != NEWLINE ) {
- --p;
- if( p <= buffer ) { *bp = buffer; return FALSE; }
- }
- *bp = p;
- return TRUE;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean end_line( char **bp )
- *
- * move buffer pointer to next newline character
- *
- * contents of bp updated to new position in buffer, which is the next
- * newline
- *
- * returns: 1 successful
- * 0 end of buffer (NULL) encountered
- *---------------------------------------------------------------------------*/
- Boolean end_line( char **bp )
- {
- char *p;
-
- p = *bp;
- if( *p == NULL ) return FALSE;
- while( *p != NEWLINE ) {
- ++p;
- if( *p == NULL ) { *bp = p; return FALSE; }
- }
- *bp = p;
- return TRUE;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- *
- * announce program version and date
- *
- *---------------------------------------------------------------------------*/
- void announce( char *version_string, char *date_string )
- {
- #ifdef __MSDOS__
- int vlength, dlength, i;
- #else
- int vlength, dlength, i, k;
- #endif
-
- vlength = strlen( version_string );
- dlength = strlen( date_string );
-
- #ifdef __MSDOS__
-
- if( dlength > 0 ) {
- printf( "\n\xc9" );
- for( i=0; i < vlength+4; i++ ) printf( "\xcd" );
- printf( "\xd1" );
- for( i=0; i < dlength+4; i++ ) printf( "\xcd" );
- printf( "\xbb\n\xba %s \xb3 %s \xba",
- version_string, date_string );
- printf( "\n\xc8" );
- for( i=0; i < vlength+4; i++ ) printf( "\xcd" );
- printf( "\xcf" );
- for( i=0; i < dlength+4; i++ ) printf( "\xcd" );
- printf( "\xbc\n" );
- } else {
- printf( "\n\xc9" );
- for( i=0; i < vlength+4; i++ ) printf( "\xcd" );
- printf( "\xbb\n\xba %s \xba", version_string );
- printf( "\n\xc8" );
- for( i=0; i < vlength+4; i++ ) printf( "\xcd" );
- printf( "\xbc\n" );
- }
-
- #else
-
- if( dlength > 0 ) {
- k = (dlength+vlength+8+1)/2;
- printf( "\n*" );
- for( i=0; i < k; i++ ) printf( " *" );
- if( IS_EVEN(dlength+vlength) )
- printf( "\n* %s * %s *", version_string, date_string );
- else
- printf( "\n* %s * %s *", version_string, date_string );
- printf( "\n*" );
- for( i=0; i < k; i++ ) printf( " *" );
- printf( "\n" );
- } else {
- k = (vlength+4+1)/2;
- printf( "\n*" );
- for( i=0; i < k; i++ ) printf( " *" );
- if( IS_EVEN(vlength) )
- printf( "\n* %s *", version_string );
- else
- printf( "\n* %s *", version_string );
- printf( "\n*" );
- for( i=0; i < k; i++ ) printf( " *" );
- printf( "\n" );
- }
-
- #endif
-
- return;
- }
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- *
- * convert string buffer to upper case
- *
- *---------------------------------------------------------------------------*/
- char *upcase( char *string )
- {
- char *p;
-
- p = string;
- while( *p ) { *p = UPPER( *p ); p++; }
- return string;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- *
- * convert string buffer to lower case
- *
- *---------------------------------------------------------------------------*/
- char *dncase( char *string )
- {
- char *p;
-
- p = string;
- while( *p ) { *p = LOWER( *p ); p++; }
- return string;
- }
-
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * char *itoh( int i, char *string )
- *
- * convert an integer to a string of hex characters
- *---------------------------------------------------------------------------*/
- char *itoh( int i, char *string )
- {
- int k;
- int j;
- char *p;
-
- /* load the character string with hex values */
- p = string;
- *p = NULL;
- if( i < 0 ) return string;
-
- k = i;
- if( k == 0 ) {
- *p++ = itohc( k );
- *p = NULL;
- } else {
- while( k > 0 ) {
- j = k % HEX_RADIX;
- *p++ = itohc( j );
- k /= HEX_RADIX;
- }
- *p = NULL;
-
- /* mirror flip */
- p = string;
- sflip( p );
- }
-
- return string;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * char *ltoh( long i, char *string )
- *
- * convert a long integer to a string of hex characters
- *---------------------------------------------------------------------------*/
- char *ltoh( long i, char *string )
- {
- long k;
- int j;
- char *p;
-
- /* load the character string with hex values */
- p = string;
- *p = NULL;
- if( i < 0 ) return string;
-
- k = i;
- if( k == 0 ) {
- *p++ = itohc( (int)k );
- *p = NULL;
- } else {
- while( k > 0 ) {
- j = (int) (k % HEX_RADIX);
- *p++ = itohc( j );
- k /= HEX_RADIX;
- }
- *p = NULL;
-
- /* mirror flip */
- p = string;
- sflip( p );
- }
-
- return string;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * char itohc( int i )
- *
- * convert an integer in the range 0 <= i <= 15 to a hex character
- *---------------------------------------------------------------------------*/
- char itohc( int i )
- {
- char *p = "0123456789ABCDEF";
-
- if( i < 0 || i > 15 )
- return NULL;
- else
- return p[i];
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * char *sflip( char *string )
- *
- * mirror-flip a string of characters
- *---------------------------------------------------------------------------*/
- char *sflip( char *string )
- {
- char *p1, *p2;
-
- /* point to first and last characters */
- p1 = string;
- while( *p1 ) ++p1;
- p2 = p1 - 1;
- p1 = string;
-
- /* swap characters */
- while( p2 > p1 ) {
- SWAP( *p1, *p2 );
- ++p1;
- --p2;
- }
-
- return string;
- }
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- *
- * left justify a text string
- *
- *---------------------------------------------------------------------------*/
- char *ljust( char *string )
- {
- char *sp, *p;
-
- if( *string != BLANK && *string != TAB ) return string;
-
- /* skip white */
- sp = string;
- while( *sp == BLANK || *sp == TAB && *sp ) ++sp;
-
- /* move */
- p = string;
- while( *sp ) *p++ = *sp++;
- *p = NULL;
-
- return string;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * struct tab_info expand_tabs( int n, char *in_ptr, char *out_ptr
- * long maxchars )
- *
- * Function to expand the tabs in *in_ptr and put the result into
- * *out_ptr. The number of spaces that will be put in place of tabs
- * is n
- *
- * expand_tabs returns the number of tab substitutions performed and the
- * number of spaces inserted. If the output buffer is too small, values
- * of -1 are returned instead
- *---------------------------------------------------------------------------*/
- Tab_Info expand_tabs( int n, char *in_ptr, char *out_ptr, long maxchars )
- {
- int npos = 0; /* position from beginning of instring */
- /* or from last '\n' */
- int nfill, i;
- long char_count = 0;
- char c, *in, *out;
- Tab_Info count;
-
-
- count.ntabs = 0;
- count.nspaces = 0;
-
- in = in_ptr;
- out = out_ptr;
- c = *in;
- while( c != NULL ) {
- ++npos;
- ++char_count;
- if( char_count > maxchars ) {
- count.ntabs = -1;
- count.nspaces = -1;
- return count;
- }
-
- if( c == TAB ) { /* found a tab */
- ++count.ntabs;
- if( n != 0 ) { /* skip if tab = 0 spaces */
-
- /* spaces to next tab stop */
- nfill = ( ((npos-1) / n) + 1 ) * n + 1 - npos;
-
- /* check for possible overflow */
- char_count += nfill - 1;
- if( char_count > maxchars ) {
- count.ntabs = -1;
- count.nspaces = -1;
- return count;
- }
-
- c = BLANK;
- for( i=0; i < nfill; i++) *out++ = c;
- npos += nfill - 1;
- count.nspaces += nfill;
- }
- } else {
- if( c == NEWLINE ) npos = 0;
- *out++ = *in;
- }
- c = *(++in);
- }
- *out = NULL;
-
- return count;
- }
-
-
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean next_word( char **bp, char *word, int *n )
- *
- * retrieve next word from a buffer
- *
- * A word is assumed to consist of sequential alphanumeric characters or
- * an underscore. Anything else is a word delimiter
- *
- * entry: bp pointer to the address of the input buffer pointer
- *
- * exit: word contents of next word
- * n number of characters in word, excluding the NULL
- * *bp points to 1st char after word
- *
- * returns: 1 successful
- * 0 NULL encountered
- *---------------------------------------------------------------------------*/
- Boolean next_word( char **bp, char *word, int *n )
- {
- char *wp;
-
- /* skip to next word */
- wp = word;
- *n = 0; *wp = NULL;
- while( !WORD_CHAR( **bp ) && **bp ) ++(*bp);
- if( **bp == NULL ) return FALSE;
-
- /* transfer a word */
- *n = 1; *wp++ = **bp; ++(*bp); /* 1st character */
- while( WORD_CHAR( **bp ) ) {
- *wp++ = **bp;
- ++(*n);
- ++(*bp);
- }
- *wp = NULL;
- return TRUE;
- }
-
-
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean next_word_num( char **bp, char *word, int *n )
- *
- * retrieve next word from a buffer (word can also be a number)
- *
- * A word is assumed to consist of sequential alphanumeric characters or
- * any of the following special characters: . + - _
- * Anything else is a word delimiter
- *
- * entry: bp pointer to the address of the input buffer pointer
- *
- * exit: word contents of next word
- * n number of characters in word, excluding the NULL
- * *bp points to 1st char after word
- *
- * returns: 1 successful
- * 0 NULL encountered
- *---------------------------------------------------------------------------*/
- Boolean next_word_num( char **bp, char *word, int *n )
- {
- char *wp;
-
- /* skip to next word */
- wp = word;
- *n = 0; *wp = NULL;
- while( !WORD_NUM_CHAR( **bp ) && **bp ) ++(*bp);
- if( **bp == NULL ) return FALSE;
-
- /* transfer a word */
- *n = 1; *wp++ = **bp; ++(*bp); /* 1st character */
- while( WORD_NUM_CHAR( **bp ) ) {
- *wp++ = **bp;
- ++(*n);
- ++(*bp);
- }
- *wp = NULL;
- return TRUE;
- }
-
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Boolean is_blank( char *string )
- *
- * test character string for emptiness
- *
- * returns: 1 string is empty or contains only blanks or tabs
- * 0 string is not empty
- *---------------------------------------------------------------------------*/
- Boolean is_blank( char *string )
- {
- char *sp;
-
- sp = string;
- while( *sp ) {
- if( *sp != BLANK && *sp != TAB ) return FALSE;
- ++sp;
- }
-
- return TRUE;
- }
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * Write a message to stdout
- *
- * The line after the message is cleared
- * Cursor is left at column
- * If nextline = TRUE, a linefeed is printed before the message
- * If lineafter = TRUE, a linefeed is printed after the message
- *
- *---------------------------------------------------------------------------*/
- void print_msg( Boolean nextline, Boolean lineafter, int n, ... )
- {
- char *sp;
- register int i;
- int k, length;
- va_list argp;
-
-
- if( nextline ) putchar( NEWLINE );
-
- length = 0;
- putchar(CR);
- va_start( argp, n );
- for( k=0; k < n; k++ ) {
- sp = va_arg( argp, char * );
- printf( "%s", sp );
- length += strlen(sp);
- }
- va_end(argp);
-
- for( i=0; i < 79 - length; i++ ) putchar(BLANK);
- putchar(CR);
-
- if( lineafter ) putchar( NEWLINE );
-
- fflush( stdout );
- }
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * void moreprint( char *string )
- *
- * Function to print the message in *string to the screen, pausing every
- * (TEXT_ROWS - 1) lines (similar to the Unix more utility)
- *
- *---------------------------------------------------------------------------*/
- void moreprint( char *string )
- {
- register int i;
- char c, *strp;
- #if __TURBOC__
- char *msg = "<*>Press any key (q to quit)";
- #else
- char *msg = "<*>Press ENTER to continue (Q ENTER to quit)";
- #endif
-
-
- strp = string;
-
- #if __TURBOC__
-
- while( *strp ) {
- /* output one screenful of text */
- clrscr();
- for( i = 0; *strp && i < TEXT_ROWS - 1; i++ )
- print_line( ON, &strp );
-
- /* "more" */
- if( i == TEXT_ROWS - 1 ) {
- if( *strp == NULL ) putchar( NEWLINE );
- c = moreprint_pause( msg );
- if( c == 'q' || c == 'Q' ) {
- putchar( NEWLINE );
- return;
- }
- }
- }
-
- /* final pause */
- while( i < TEXT_ROWS-1 ) { ++i; putchar( NEWLINE ); }
- c = moreprint_pause( msg );
-
- #else
-
- while( *strp ) {
- /* output one screenful of text */
- for( i = 0; *strp && i < TEXT_ROWS - 2; i++ )
- print_line( ON, &strp );
-
- /* "more" */
- if( i == TEXT_ROWS - 2 ) {
- if( *strp == NULL ) putchar( NEWLINE );
- c = moreprint_pause( msg );
- if( c == 'q' || c == 'Q' ) {
- putchar( NEWLINE );
- return;
- }
- }
- }
-
- /* final pause */
- while( i < TEXT_ROWS-2 ) { ++i; putchar( NEWLINE ); }
- c = moreprint_pause( msg );
-
- #endif
-
-
- return;
- }
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * char moreprint_pause( char *msg )
- *
- * Function to put a "press any key" message on the screen and wait for
- * a keypress. Message text is in *msg, and it has to contain an asterisk
- * if this is being compiled with TURBO C
- *
- * This function is designed for use by moreprint
- *
- * Returns the first character pressed
- *---------------------------------------------------------------------------*/
- char moreprint_pause( char *msg )
- {
- char c, *p;
- int i1;
-
-
- /* print the "pause" message */
- p = msg;
- while( *p ) { putchar(*p); ++p; }
- putchar( CR );
-
-
- /* wait for a keypress */
-
- #if __TURBOC__
-
- /* blink the asterisk */
- i1 = (int) ( strchr( msg, '*' ) - msg + 1 );
- _setcursortype( _NOCURSOR );
- while( !kbhit() ) {
- /* off */
- gotoxy( i1, TEXT_ROWS );
- putchar( BLANK );
- delay( 100 );
-
- /* on */
- gotoxy( i1, TEXT_ROWS );
- putchar( '*' );
- delay( 100 );
- }
-
- /* erase the "pause" message */
- p = msg;
- putchar( CR );
- while( *p++ ) putchar( BLANK );
- putchar( CR );
-
- /* quit now? */
- c = (char) getch();
- while( kbhit() != 0 ) getch(); /* flush extra key hits */
- _setcursortype( _NORMALCURSOR );
- if( c == 'q' || c == 'Q' ) {
- putchar( NEWLINE );
- return c;
- }
-
- #else
-
- /* simulate kbhit() */
- c = getc(stdin);
-
- /* erase the "pause" message */
- p = msg;
- putchar( CR );
- while( *p++ ) putchar( BLANK );
- putchar( BLANK );
- putchar( CR );
-
- #endif
-
- return c;
- }
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * void print_line( int crlf, char **text_ptr )
- *
- * print one line of text to the stdout device (including CR+LF if crlf
- * is ON)
- *
- * input: text_ptr Pointer to the address of a pointer in the calling
- * program into the text buffer. Output starts from
- * the position in the text buffer pointed to by the
- * contents of text_ptr
- *
- * output: text_ptr The contents of text_ptr, which in turn is a
- * pointer, is updated to the address of the new
- * position in the text buffer after the line has
- * written. This new position is the byte after a
- * newline has been encountered
- *---------------------------------------------------------------------------*/
- void print_line( int crlf, char **text_ptr )
- {
- char *p;
-
- p = *text_ptr;
- while( *p != NEWLINE && *p ) putchar( *p++ );
- if( *p == NEWLINE ) {
- ++p;
- if( crlf ) {
- putchar(CR);
- putchar(LF);
- }
- }
- *text_ptr = p;
-
- return;
- }
-
-
-
-
-
-
-
- #ifdef __TURBOC__
- /*-----------------------------------------------------------------------------
- *
- * console version of print_line
- *
- *---------------------------------------------------------------------------*/
- void cprint_line( int crlf, char **text_ptr )
- {
- char *p;
-
- p = *text_ptr;
- while( *p != NEWLINE && *p ) putch( *p++ );
- if( *p == NEWLINE ) {
- ++p;
- if( crlf ) {
- putch(CR);
- putch(LF);
- }
- }
- *text_ptr = p;
-
- return;
- }
- #endif
-
-
-
-
-
-
-
-
-
- /*-----------------------------------------------------------------------------
- * void parse_args( char string[], int *nargs, double args[] )
- *
- * Function to parse (double) floating arguments from a null-terminated
- * string buffer
- *
- * entry: string[] null-terminated string containing numbers to
- * decode
- *
- * exit: *nargs number of numbers decoded
- * args[] vector containing decoded (double) floating
- * numbers
- *
- * function dependencies: none
- * header files: ctype.h, stdio.h
- *---------------------------------------------------------------------------*/
- #ifndef NO_FLOAT
-
- void parse_args( char string[], int *nargs, double args[] )
- {
- int i, j, k, do_flag;
- char c, *tmpstr;
- double fnum;
-
-
- tmpstr = cvector( 0, 80 );
-
- if( *string == NULL )
- *nargs = 0;
- else {
- *nargs = 0; i = 0; do_flag = 1;
- while( string[i] != NULL && do_flag ) {
- /* skip leading white space */
- while( isspace( string[i] ) ) i++;
-
- /* put number into tmpstr */
- j = 0;
- while( string[i] != NULL && !isspace((c = string[i])) ) {
- tmpstr[j++] = c;
- i++;
- }
-
- /* decode number in tmpstr */
- if( j > 0 ) {
- tmpstr[j] = NULL;
- fnum = atof( tmpstr );
-
- /* valid number was returned */
- if( fnum != 0.0 ) {
- args[*nargs] = fnum;
- (*nargs)++;
-
- /* zero returned--check for an actual zero */
- } else {
- k = 0;
- if( (c=tmpstr[k]) == '+' || c == '-' ) k++;
- if( (c=tmpstr[k]) != '0' ) {
- if( c != '.' )
- do_flag = 0; /* not a number */
- else { /* is a decimal point */
- while( (c=tmpstr[++k]) == '0' );
- if( c == NULL || isspace(c) ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else { /* check for e- or d-floating */
- if( c == 'e' || c == 'E' ||
- c == 'd' || c == 'D' ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else
- do_flag = 0; /* not a number */
-
- } /* e- or d-floating format check */
-
- } /* is a decimal point */
-
- } /* 1st char != 0 */
-
- else { /* 1st char = '0' */
- while( (c=tmpstr[++k]) == '0' );
- if( c == NULL || isspace(c) ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else { /* check for decimal point */
- if( c == '.' ) {
- while( (c=tmpstr[++k]) == '0' );
- if( c == NULL || isspace(c) ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else { /* check for e- or d-floating */
- if( c == 'e' || c == 'E' ||
- c == 'd' || c == 'D' ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else
- do_flag = 0; /* not a number */
-
- } /* e- or d-floating format check */
-
- } /* is a decimal point */
- else {
- if( c == 'e' || c == 'E' ||
- c == 'd' || c == 'D' ) {
- args[*nargs] = fnum;
- (*nargs)++;
- } else
- do_flag = 0; /* not a number */
-
- } /* not a d.p., e- or d-floating check */
-
- } /* decimal point check */
-
- } /* 1st char = '0' */
-
- } /* check for actual zero */
-
- } /* j > 0 (input string not empty) */
-
- } /* decoding loop */
-
- } /* input string not NULL */
-
- free_cvector( tmpstr, 0 );
- return;
- }
-
- #endif
-
-
-
-
-
-