Viewing TEXT75 files



Post: #2

I was trying to view a bunch of TEXT75 files from the swap disks in the HP Museum site and was frustrated by the control information that surrounded the data. So I put together the following program which should work on most systems.

I have probably rediscovered the wheel, so if there is something better, do let me know and I will remove this posting.

Program takes a single argument which is assumed to be a TEXT75 file and prints the converted contents on standard output.

--------------------------------------------------------

/*
* pr_text75 -- convert TEXT75 files to ASCII
* Vassilis Prevelakis, CS Dept, Drexel University (2004/3/10)
*
* TEXT75 files use a format similar to that of BASIC programs.
* They have a short header, followed by lines of the format
* 2-byte line number in BCD
* 1-byte line length
* printable text.
*
* pr_text75 has been put together so as to skip the header and
* then print the contents of the file by printing the line number
* followed by the text.
*
* Unprintable characters in the text are printed in expanded form
* i.e. character code 8A will be printed as [8A].
*
* Quick hack to deal with swap-file format files. These have an
* additional 32 byte header. The hack involves looking for
* a bunch of zeros in the TEXT75 header in the file, and if this
* fails, look for the same info 32 bytes later.
* Given the richness of LIF files (i.e. loose standards), this hack
* is bound to fail on some file, so it should be replaced with something
* more decent.
*/
#include <stdio.h>
#include <stdlib.h>

char tohex(char c)
{
return((c < 10) ? (c + '0') : (c + 'A' - 10));
}

int get_str(char *cp, int n, FILE *fd)
{
int c;
while (n-- > 0)
{
if ((c = fgetc(fd)) < 0)
return(-1);
if (isprint(c))
*cp++ = c;
else {
*cp++ = '[';
*cp++ = tohex(c >> 4);
*cp++ = tohex(c & 0xF);
*cp++ = ']';
}
}
*cp = '\0';
return(0);
}
int rd_short(FILE *fd)
{
int msb, lsb;

if ((lsb = getc(fd)) < 0)
return(-1);
if ((msb = getc(fd)) < 0)
return(-1);
return((msb << 8) | lsb);
}

main(int argc, char **argv)
{
unsigned char buf[1025]; // worst case of a string with unprintable characters
int l, c;
char *fname;
FILE *fd;

fname = argv[1];
if ((fd = fopen(fname, "r")) == NULL) {
fprintf(stderr, "Could not open %s.\n", fname);
perror("fopen");
exit(1);
}

// if its just the file then we need to skip 24 bytes,
// if its a swap file, we need to skip another 32
fseek(fd, 26, SEEK_SET);
if ((l = rd_short(fd)) != 0)
{
fseek(fd, 30, SEEK_CUR); // two bytes we have read + 30 = 32
if ((l = rd_short(fd)) != 0)
{
fprintf(stderr, "File is not TEXT75?\n");
exit(1);
}
}

for(;;) {
// read line-number
if ((l = rd_short(fd)) < 0)
break;
// read string length
if ((c = getc(fd)) < 0)
break;
// read string
if (get_str(buf, c, fd) < 0)
break;
// if End-of-File sequence, exit
if (l == 0xA999 && c == 2)
break;
// print line-number: string
printf("%04x %s\n", l, buf);
};
exit(0);
}


Post: #3

There's also a text75 program in my 'LIF Utilities for Linux' (available from http://www.hpcc.org/). It reads an HP75 text file on standard input and outputs a more sane version to standard output. It's written in C and should be fairly portable. There are other translation filters there too, for HP LIF1 text files, HP41 programs, and so on...


Forum Jump: