Consultor Eletrônico



Kbase P60672: C program to display a Database block in ASCII
Autor   Progress Software Corporation - Progress
Acesso   Público
Publicação   24/12/2003
Status: Unverified

GOAL:

C program to display a Database block in ASCII

FACT(s) (Environment):

Progress V6.x

FACT(s) (Environment):

Progress V7.x

FACT(s) (Environment):

Progress V8.x

FIX:

Compile the source with your system's  C compiler:
cc viewblock.c -o viewblock  OR  make viewblock

Use the following syntax:
viewblock <database name> dbkey

Use your favorite pager to page the output.
Example: viewblock demo 128 | pg

Restriction: Only single volume databases.

The program:

#include  <stdio.h>
#include  <math.h>

long lseek();
void
syserr(msg)
   char *msg;
{
extern int errno, sys_nerr;
extern char *sys_errlist[];

 fprintf(stderr, "\nERROR: %s (%d", msg, errno);
 if (errno > 0 && errno < sys_nerr)
     fprintf(stderr, "; %s)\n", sys_errlist[errno]);
 else
   fprintf(stderr,")\n");
 exit(1);
}

FILE *fpdb;
short int blocksize;

main(argc,argv)
int argc;
char *argv[];
{
 FILE *fopen(), *fplock;
 char dbname[70], lockfile[70];
 short int dbversion;
 long int dbblocks, dbkey=0, blocknum=0, dbwater=0, offset;

 if (argc < 3)        /* Te weinig opties: error */
 {
   printf("%s: Usage: %s <database> dbkey.\n",argv[0],argv[0]);
   exit(1);
 }

 if (argc > 3)        /* Te veel opties: error */
 {
   printf("%s: Too many options.\n",argv[0]);
   exit(1);
 }

 strcpy(dbname,argv[1]);
 strcat(dbname,".db");
if (( fpdb = fopen(dbname, "rb" )) == NULL)
 {
   printf("%s: Could not find or open file %s\n",argv[0],dbname);
   syserr("");
   exit(1);
 }

 strcpy(lockfile,argv[1]);
 strcat(lockfile,".lk");
 printf("\n                Blockview. Version 1.0 by Peter de Jong.\n
\n");
 if (( fplock = fopen(lockfile,"r")) != NULL)
 {
   printf("WARNING: The lockfile %s exists!\n\n",lockfile);
   fclose(fplock);
 }

 printf("                   Database name: %s\n",dbname);

 if (fseek(fpdb, 16, 0) == -1)
       syserr("fseek");
 if (fread(&dbversion, 1, 2, fpdb) != 2)
       syserr("fread");
printf("         Database version number: %d\n",dbversion);

 if (fseek(fpdb, 18, 0) == -1)
       syserr("fseek");
 if (fread(&blocksize, 1, 2, fpdb) != 2)
       syserr("fread");
 blocksize = (blocksize * 512);
 printf("              Database blocksize: %d\n",blocksize);

 if (fseek(fpdb, 24, 0) == -1)
       syserr("fseek");
 if (fread(&dbblocks, 1, 4, fpdb) != 4)
 syserr("fread");
 printf("    Number of blocks in database: %d\n",dbblocks);

 if (dbblocks == 0) {
   printf("\nERROR: Multi Volume database or masterblock corrupted.\n
Number of database blocks = %d.\n",dbblocks);
   exit(1);
if (fseek(fpdb, 48, 0) == -1)
       syserr("fseek");
 if (fread(&dbwater, 1, 4, fpdb) != 4)
       syserr("fread");
 printf("            Database blocks used: %d\n",dbwater);

 /* MAINLOOP */
 dbkey = atoi(argv[2]);

 if (dbkey % 32 || dbkey < 1)
 {
   printf("\nERROR: %d is not a multiple of 32.\n",dbkey);
   exit(1);
 }

 printf("            Database key (dbkey): %d\n",dbkey);

 if (dbkey > (dbwater * 32))
 {
   printf("\nERROR: %d is too large for the database.\n",dbkey);
   exit(1);
 }
offset = (((dbkey / 32) -1) * blocksize);
 printf("                     file offset: %d\n\n", offset);

 if (fseek(fpdb, offset, 0) == -1)
    syserr("fseek");

 hd(fpdb,blocksize);

 /* Cleaning up */
 fclose(fpdb);
 exit(0);
} /* main */

hd(fpdb,blocksize)
FILE *fpdb; {
       int i; char w;
       int offset, cnt, hi, lo, word[8];
       offset = 0;
       cnt = 8;

       while (cnt == 8) {
               puthex(offset, 4);
               putchar(':');
          .     putchar(' ');
               for (cnt = 0; cnt < 8; ) {
                       if ((hi = getc(fpdb)) == EOF) break;
                       offset++;
                       if ((lo = getc(fpdb)) == EOF) {
                               word[cnt++] = (hi << 8);
                               break;
                       }
                       else    {
                               word[cnt++] = (hi << 8) + lo;
                               offset++;
                       }
 for (i = 0; i < cnt; i++) {
                       puthex(word[i], 4);
                       putchar(' ');
               }
               for ( ; i < 8; i++) printf("     ");
               printf(" | ");
               for (i = 0; i < cnt; i++) {
                       putcx(word[i] >> 8);
                       putcx(word[i]);
               }
               putchar('\n');
               /* Leave after displaying the db block */
               if (offset > blocksize) return;
       }
       if (cnt != 0) {
               puthex(offset, 4);
               putchar('\n');
       }
}

puthex(n, size) {
       if (size > 1) puthex(n >> 4, size - 1);
       putchar("0123456789ABCDEF"[n & 15]);
}

putcx(c) {
       c = c & 255;
       if (c >= 32 && c <= 127) putchar(c);
       else putchar('.');
}
/* EOF */


NOTE: This program is tested on most major UNIX systems, this does not
     imply it will compile and run on your system.
     This program is not supported. Tested on V6, V7 & V8 Databases..