} } >>> If \`'strlen() argv[i] ) == 2' the switch is followed by a space to be deleted when more input is awaited. \<<< if( (int) strlen((char *) argv[i] ) == 2 ){ if( ++i == argc ) bad_arg; } switch( *(p+1) ){ case 'b':{ ` break; } case 'c':{ ` break;} case 'e':{ ` break; } case 'f':{ ` break; } case 'F':{ ` break; } case 'g':{ ` break; } case 'h':{ ` break; } case 'i':{ ` break; } case 'l':{ ` break; } case 'P':{ ` break; } case 'S':{ ` break; } case 's':{ ` break; } case 't':{ ` break; } case 'u':{ ` break; } case 'v':{ ` break; } case 'x':{ ` break; } case '.':{ ` break; } default:{ bad_arg; } } >>> The following is to allow for commands \`'htlatex -f/../source/foo.tex' which draw files from other directories for latex, but use the current directory for tex4ht.c (and t4ht.c). The character immediately after \`'-f' is a directory indicator character. The \`'-f/' requests a search for the indicated file to take place in the current directory, not in a remote one. \ <<< p = p + 2; in_name = p + (int) strlen((char *) p ); while( *in_name != *p ){ in_name--; } in_name++; >>> Suboptions for \`'-h'. \ <<< { char trace = *(p+2); if (trace == 'A' || trace == 'e') { ` } if (trace == 'A' || trace == 'f') { ` } if (trace == 'A' || trace == 'F') { ` } if (trace == 'A' || trace == 's') { ` } if (trace == 'A' || trace == 'g') { ` } if (trace == 'A' || trace == 'v') { ` } if (trace == 'A' || trace == 'V') { ` } else { bad_arg; } } >>> The following is incomplete!!! \ <<< "improper command line\ntex4ht [-f ]in-file[.dvi]\n" " [-. ] replacement to default file extension name .dvi\n" " [-c ] choose named segment in env file\n" " [-e ]\n" " [-f ] remove path from the file name\n" " [-F ] replacement for missing font characters; 0--255; default 0\n" " [-g ]\n" " [-h[efFgsvVA]] trace: e-errors/warnings, f-htf, F-htf search\n" " g-groups, s-specials, v-env, V-env search, A-all\n" " [-i ]\n" " [-l ]\n" " [-P(*| )] permission for system calls: *-always, filter\n" " [-S ]\n" " [-s ] default: -s4cs; multiple entries allowed\n" " [-t ]\n" " [-u10] base 10 for unicode characters\n" " [-utf8] utf-8 encoding for unicode characters\n" " [-v ] replacement for the given dvi version\n" " [-xs] ms-dos file names for automatically generated gifs\n" >>> Line breaks within command lines should be physically given. \Section{I/O Files} \ <<< #ifndef PATH_MAX #define PATH_MAX 512 #endif >>> \Verbatim ../html.dir/a.out a -s"--- needs --- %%1.idv[%%2] ==> %%3 --- " -b"--- characters --- \EndVerbatim \SubSection{Open Input} \ <<< static FILE* dvi_file; >>> \ <<< dvi_file = stdin; >>> Below: If input is from stdin which is not a console device, switch it to binary mode. Warning `statement with no effect' under \`'gcc -Wall' on non-Windows. This is not a problem; SET_BINARY is a no-op. \ <<< if( *in_name != '\0' ){ ` } #ifdef KWIN32 else if (!isatty(fileno(stdin))) SET_BINARY(fileno(stdin)); #endif >>> \ <<< BOOL tag; job_name_n = (int) strlen( in_name ); job_name = m_alloc(char, job_name_n+6); (IGNORED) strcpy((char *) job_name, in_name); tag = job_name_n < 3; if( !tag ){ tag = !eq_str( job_name+job_name_n-` ,` ); } if( tag ){ job_name_n+=` ; (IGNORED) strct(job_name, ` ); } if( (dvi_file = fopen(job_name, READ_BIN_FLAGS)) == NULL ) { ` } ` >>> \ <<< ( (ext==NULL)? 4 : (int) strlen((char *) ext) ) >>> \ <<< ( (ext==NULL)? ".dvi" : ext ) >>> \ <<< static U_CHAR *ext = NULL; >>> \ <<< ext = p+1; >>> The following tries to remove an extension from the filename, before adding the `.dvi' extension. This can help with ht scripts of the form \Verbatim $1 $2 $1 $2 $1 $2 tex4ht $2 t4ht $2 \EndVerbatim in cases that the users insert for \`'$2' file names with extension. \ <<< { int i; for(i=job_name_n-5; i; i--){ if( job_name[i] == '.' ){ job_name[i] = '\0'; job_name_n = i + ` ; (IGNORED) strct(job_name, ` ); break; } } if( (dvi_file = fopen(job_name, READ_BIN_FLAGS)) == NULL ){ warn_i_str(1, job_name); bad_in_file(job_name); } } >>> \ <<< static char* job_name; static int job_name_n; >>> strcat should be in string.h, but c++ doesn't find it there. We use it just for concatenating an extension of file name. Should have the interface \`'char *strcat( (char *, const U_CHAR *) );'. \ <<< static void strct( ARG_II(char *, const U_CHAR *) ); >>> \ <<< `[ static void strct( str1, str2 ) U_CHAR * str1`; const U_CHAR * str2 ;{ U_CHAR * ch; ch = str1 + (int) strlen((char *) str1); (IGNORED) strcpy((char *) ch, str2 ); } >>> \SubSection{Open Root Html File} \ <<< U_CHAR *name=0; if( *out_name == '\0' ) { if( *in_name == '\0' ){ `} else { ` } } else{ ` } no_root_file = name; >>> We want to wait with actually opening the file output file until the last minute, to allow a special to change the extension name from the tex file. That last minute is taken to be when a cll to openning ort closing a file occurs, or when output is to be written into the file. \ <<< if( no_root_file ){ open_o_file(); } >>> \ <<< static void open_o_file( ARG_I(void) ); >>> \ <<< static void open_o_file(MYVOID) { ` cur_o_file = root_file = open_html_file(no_root_file); no_root_file = (char *) 0; } >>> % free((void *) no_root_file); \ <<< struct files_rec* p; p = m_alloc(struct files_rec, 1); if( opened_files != (struct files_rec*) 0 ) opened_files->prev = p; p->prev = (struct files_rec *) 0; p->next = opened_files; opened_files = p; p->name = no_root_file; p->file = >>> \ <<< if( !no_root_file ){ ` if( !` ){ put_char('\n'); } } >>> \ <<< if( no_root_file ){ U_CHAR *name; name = m_alloc(char, 256); (IGNORED) strcpy((char *) name, (char *) no_root_file ); free((void *) no_root_file); no_root_file = name; name += (size_t) strlen((char *) name); while( *(--name) != '.' ); name++; while( special_n-- ){ if( (no_root_file+253) == name ) name--; *name++ = get_char(); } *name = '\0'; } else { U_CHAR str[256], *p; p = str; while( special_n-- ){ *p++ = get_char(); } *p = '\0'; warn_i_str(43,str); } >>> \ <<< static U_CHAR *no_root_file; >>> \ <<< bad_arg; >>> \ <<< int n = (int) strlen((char *) job_name ); name = m_alloc(char, 6 + n); (IGNORED) strcpy((char *) name, (char *) job_name); n -= 4; *(name + n) = '\0'; (IGNORED) strct(name,".html"); #ifdef HTM name[n+4] ='\0'; #endif >>> \ <<< int tag = 1; int n = (int) strlen( out_name ); name = m_alloc(char, 6 + n); (IGNORED) strcpy((char *) name, out_name); while( n-- ) tag = tag && (*(name+n) != '.') ; if( tag ) (IGNORED) strct(name,".html"); #ifdef HTM name[n+4] = '\0'; #endif >>> \ <<< static FILE* open_html_file( ARG_I(char*) ); >>> \ <<< `[ static FILE* open_html_file(name) char* name ;{ FILE* file; char* str; str = m_alloc(char, (int) strlen((char *) name) + 1); (IGNORED) strcpy((char *) str, (char *) name); (IGNORED) printf(" file %s\n", str); (IGNORED) fprintf(log_file, "File: %s\n", str); if( (file = fopen(str, WRITE_TEXT_FLAGS)) == NULL ) bad_in_file(str); free((void *) str); return file; } >>> \ <<< static FILE *out_file = (FILE *) 0, *root_file = (FILE *) 0, *cur_o_file = (FILE *) 0; >>> \SubSection{Close Output} \ <<< if( root_file != (FILE *) 0 ) (IGNORED) fclose(root_file); >>> \SubSection{Get Input-File Length} Files must have length divisible by four and have 4 to 7 \`'trail' characters. Another problem I ran into is that fileno is unavailable to both compiler and linker if I turn on ANSI compilation. I checked where you use it, and it is in only one place, to find the file length of the DVI file. Your code: \Verbatim { struct STSTAT temp; (IGNORED) fstat (fileno(dvi_file), &temp); file_len = (long) temp.st_size; if( (file_len % 4) != 0 ) bad_dvi; } \EndVerbatim If you change this to use ftell and fseek, you'll have gained ANSI compatibility (and therewith portability). I tried the following code instead of yours: \ <<< { long curr_pos; curr_pos = ftell(dvi_file); (IGNORED) fseek(dvi_file, 0, SEEK_END); file_len = ftell(dvi_file); (IGNORED) fseek(dvi_file, curr_pos, ` ); if( (file_len % 4) != 0 ) bad_dvi; } >>> % SEEK_SET); To the best of my nowledge, this works exactly like your code (I tested it). My executable is compiled with this code. see also fgetpos and fsetpos. \Section{Coding Hints} \ifHtml[\HPage{ini (initialization) files in windows}\Verbatim \Verbatim /*************** foo.c file *******************/ #include #include #include #include // Windows-specific functions used: // _fullpath : make filename into full path // _splitpath : split a _fullpath into its component parts // GetPrivateProfileString: handle the .ini file _fullpath(path,argv[0],250); _splitpath(path,drive,dir,filname,ext); char TEXINAME[100], NOBATCHNAME[MV2]; GetPrivateProfileString("Files", "TEXINAME", NOBATCHNAME, TEXINAME, 100, "foo.ini"); GetPrivateProfileString("Strings", "SWPPACK", dSWPPACK, SWPPACK, 100,"foo.ini"); DEBFLAG=GetPrivateProfileInt("integers", "DEBFLAG",0, "foo.ini"); /*************** foo.ini file ********************/ [integers] ; DEBFLAG = 1 prints additional details DEBFLAG = 0 [files] ; texinfo TexiName = texis.bat [strings] ; swp package SWPPACK = {swpht} \EndVerbatim\EndHPage{}]\fi \ifHtml[\HPage{detecting tex tree}\Verbatim > > on a Windows machine? (How can the installer know where to put files > > without actually searching the entire hard disc.) Any ideas? > > Unfortunately, I have no idea on how to avoid a global search. a) create a file foo.tex containing hello \bye b) run tex foo.tex c) open foo.log and analyze the results. you should be able to get all the clues you need about their setup \EndVerbatim\EndHPage{}]\fi \ifHtml[\HPage{kpathsea}\Verbatim My key discovery was the library `kpathsea' which does file name look up. And in particular `kpsewhich --show-path TEXFILETYPE'. So, for example, `kpsewhich --show-path tfm' returns a colon separated list of paths to tfm files. \EndVerbatim\EndHPage{}]\fi \ifHtml[\HPage{more}\Verbatim with some help from my neighbour, i got this working at last.... you had if( *(p = gif_open[gif_flag]) ) IGNORED) strct(str,p); which we changed to p = gif_open[gif_flag]; if( p && *p) (IGNORED) strct(str,p); because if gif_open[fig_flag] is NULL (which you initialize it to be!), then the *p points to a dead end..... this applied in some other places too, see appended diff. { struct group_info *p, *last; p = stack[ stack_n ].begin; \EndVerbatim\EndHPage{}]\fi \Chapter{Structure of Dvi Files} \Section{Background} \Link[http://www.rpi.edu/\string~sofkam/DVI/dvi.html]{}{}DVI driver standards \EndLink Dvi files are consisted of three parts. \bgroup \def\.#1.#2.{% \ifcase #1 \Link{#2}{dvistrct}\or \Link{#2}{}\or \Link{#2}{}\fi #2\EndLink} \Verbatim-\ +-----------+ | \.0.preamble. | +-----------+ | \.1.pages. | +-----------+ | \.2.postamble. | +-----------+ \EndVerbatim \egroup \SubSection{Example} \Link{}{dvcd} \EndLink{} \Verbatim 000000: PRE version : 2 000002: numerator : 25400000 000006: denominator : 473628672 000010: magnification : 1000 000014: job name ( 27) : TeX output 1995.02.22:0104 000042: BOP page number : 1 000047: 0 0 0 000059: 0 0 0 000071: 0 0 0 000083: prev page offset : -00001 000087: PUSH 000088: DOWN3: -917504 000092: POP 000093: DOWN4: 42152922 000098: PUSH 000099: DOWN4: -41497562 000104: PUSH 000105: FNT_DEF1: 29 000107: checksum : -538297224 000111: scale : 655360 000115: design : 655360 000119: name : cmtt10 000127: FONT_29 000128: Char: try.htex 000163: POP 000164: Y3: 786432 000168: PUSH 000169: PUSH 000170: RIGHT3: 1310720 000174: Char:000177: POP 000178: RIGHT3: 2342903 000182: FNT_DEF1: 12 000184: checksum : 555887770 000188: scale : 655360 000192: design : 655360 000196: name : cmsy10 000204: FONT_12 000205: Char: ff /* ligature (non-printing) */ 000206: W3: 145632 000210: Char: 0x 0 000211: W0 000212: Char: A 000213: PUSH 000214: DOWN3: -237825 000218: Char: ffi /* ligature (non-printing) */ 000219: POP 000220: RIGHT3: 704510 000224: FONT_29 000225: Char: A 000226: RIGHT3: 344061 000230: Char: B 000231: POP 000232: Y0 000233: PUSH 000234: Char: 000248: POP 000249: POP 000250: DOWN3: 1572864 000254: EOP 000255: POST last page offset : 000042 000260: numerator : 25400000 000264: denominator : 473628672 000268: magnification : 1000 000272: max page height : 43725786 000276: max page width : 30785863 000280: stack size needed: 3 000282: number of pages : 1 000284: FNT_DEF1: 29 000286: checksum : -538297224 000290: scale : 655360 000294: design : 655360 000298: name : cmtt10 000306: FNT_DEF1: 12 000308: checksum : 555887770 000312: scale : 655360 000316: design : 655360 000320: name : cmsy10 000328: POSTPOST postamble offset : 000255 000333: version : 2 000334: TRAILER 000335: TRAILER 000336: TRAILER 000337: TRAILER 000338: TRAILER 000339: TRAILER \EndVerbatim %%%%%%%%%%%%%%%%%%%%%%%%%%%%% \Section{Scan Postamble} %%%%%%%%%%%%%%%%%%%%%%%%%%%%% The postamble of a \Link{dvistrct}{postamble}dvi file\EndLink{} has the following structure. It should be consistent with the preamble. \bgroup \def\.#1.{\Link{fntdef}{}#1\EndLink} \Verbatim-\ no_ops ??? >= 0 bytes NOPS, I think they are allowed here... postamble_marker 1 ubyte POST last_page_offset 4 sbytes numerator 4 ubytes denominator 4 ubytes magnification 4 ubytes max_page_height 4 ubytes max_page_width 4 ubytes max_stack 2 ubytes total_pages 2 ubytes number of pages in file ... \.FONT DEFINITIONS. ... POST_POST 1 byte postamble_offset 4 sbytes offset in file where postamble starts version_id 1 ubyte trailer >= 4 ubytes TRAILER
\EndVerbatim \egroup %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \SubSection{No Op's at the End of File} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% Verify \LinkPort\ {}eof op\EndLink{} and version number at postamble. There should be at least four trailing characters, and normally there are no more than seven. They act as signatyre and provide for file lengths that are divisible by four, aimed at machines that pack four bytes into a word. \ <<< i=0; do{ i++; file_len -= 1; (IGNORED) fseek(dvi_file, file_len, ` ); } while( (ch=get_char()) == ` ); eof_op_n = file_len; if( (i<4) || ((ch != ` ) && (ch > ` )) ) bad_dvi; version_id = ch; >>> \ <<< static int version_id; >>> The function \`'(IGNORED) fseek' enables random access to file. \ <<< 0>>> \ <<< 1>>> %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \SubSection{Find Start of Postamble} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \ <<< file_len -= 5; (IGNORED) fseek(dvi_file, file_len, ` ); if( get_char() != ` ) bad_dvi; eof_op_n -= begin_postamble = get_unt(4); (IGNORED) fseek(dvi_file, begin_postamble, ` ); >>> %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \SubSection{Find Stack Size and Number of Pages} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \ <<< if( get_char() != ` ) bad_dvi; (IGNORED) fseek(dvi_file, 16L, ` ); ` if( (stack_len = (int) get_unt(2)) < 1) bad_dvi; ` unread_pages = (int) get_unt(2); >>> \ <<< int unread_pages; >>> \ <<< static int stack_len; >>> %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \SubSection{Font Definitions} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \ <<< { ` BOOL missing_fonts; #ifndef KPATHSEA ` ` ` #endif ` missing_fonts = FALSE; ` ` ` while( (ch = get_char()) != ` ){ ` } ` if( missing_fonts ) err_i(14); #ifndef KPATHSEA `