home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Usenet 1994 October
/
usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso
/
unix
/
volume25
/
finger
/
part03
/
read_vmunix.c
< prev
next >
Wrap
C/C++ Source or Header
|
1992-04-03
|
6KB
|
213 lines
/*
* read_vmunix.c -- read data from an a.out file (for kernel _version)
* This is just awful!!
*
* Copyright (C) 1986, 1990 Philip L. Budne
*
* This file is part of "Phil's Finger Program".
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 1, or (at your option)
* any later version.
*
*/
# ifndef lint
static char *rcsid = "$Id: read_vmunix.c,v 3.0 90/07/06 13:11:37 budd Rel $";
# endif /* lint not defined */
# include "finger.h"
# if Umax != 42 && !defined(USG)
# include "args.h"
# ifndef COFF /* good old a.out */
# include <a.out.h>
/*
* N_SEGSIZ is only needed if the kernel is not an OMAGIC file.
*/
# ifdef sun
# define LMASK 0xfff /* crock, seems to work tho */
/* for Sun2,3,4 */
/*# define LOADADDR 0xff004000 /* sun4 */
/*# define LOADADDR 0x0f004000 /* sun3 */
/*# define LOADADDR 0x4000 /* sun2 */
# endif /* sun defined */
# ifdef accel
# define LMASK 0xffff
# define INCLUDE_HEADERS
# endif /* accel defined */
# ifndef N_SEGSIZ /* a sun-ism */
# include <sys/param.h> /* get CLBYTES */
# define N_SEGSIZ(a) (CLBYTES) /* simulate sun macro */
# endif /* N_SEGSIZ not defined */
# ifdef vax
# define LOADADDR 0x80000000 /* kernel load address */
# endif /* vax defined */
# ifdef ibm032 /* RT under AOS/ACIS 4.3 */
# define LOADADDR 0xe0000000 /* kernel load address */
# endif /* ibm032 defined */
# ifdef sony_news /* only tested for News-800 */
# define LOADADDR 0x80001000 /* crocked by 4k? */
# endif /* sony_news defined */
# ifdef sequent /* only tested for S3 */
# define LOADADDR 0
# endif /* sequent defined */
GLOBAL BOOL
read_vmunix( file, off, str, len )
char *file; /* file name */
long off; /* virtual address */
char *str; /* dest buffer */
int len; /* chars to read */
{
int f;
long pos, base, data, koffset;
struct exec ex;
if( off == 0L ) /* bogus offset */
return( FALSE ); /* lose quickly */
if( (f = open( file, 0 )) < 0 ) /* open /vmunix */
return( FALSE ); /* you lose */
if( read( f, &ex, sizeof( ex ) ) != sizeof( ex ) ) { /* read header */
close( f ); /* short read */
return( FALSE ); /* quit */
}
base = N_TXTOFF( ex ); /* get start of meaningfullness */
# ifdef LOADADDR
koffset = LOADADDR; /* offset into image */
# else /* LOADADDR not defined */
# ifdef LMASK
koffset = ex.a_entry & ~LMASK;
# else /* LMASK not defined */
# include <ERROR: must have one of LOADADDR and LMASK>
# endif /* LMASK not defined */
# endif /* LOADADDR not defined */
off -= koffset; /* remove kernel offset */
if( ex.a_magic == OMAGIC
# ifdef NMAGIC /* sequent lacks NMAGIC! */
|| (off < ex.a_text && ex.a_magic == NMAGIC)
# endif /* NMAGIC defined */
# ifdef SMAGIC /* sequent standalone */
|| ex.a_magic == SMAGIC
# endif /* SMAGIC defined */
) /* OMAGIC or NMAGIC text */
data = 0; /* no data offset */
# ifdef NMAGIC
else if( ex.a_magic == NMAGIC ) { /* NMAGIC data loaded on seg boundry */
int segs; /* segment size */
segs = N_SEGSIZ(ex) - 1; /* round to "segment" after text*/
data = (ex.a_text + segs - 1) & ~segs;
data -= ex.a_text; /* just get needed offset */
}
# endif /* NMAGIC defined */
# ifdef SOME_DAY_OVER_THE_RAINBOW
else if( ex.a_magic == ZMAGIC ) { /* never seen a ZMAGIC kernel!! */
base = N_SEGSIZ(ex); /* text starts on page boundry */
if( off >= ex.a_text ) {
/* something like for NMAGIC above... */
}
} /* ZMAGIC */
# endif /* SOME_DAY_OVER_THE_RAINBOW defined */
else {
# ifdef DEBUGSW
if( sw_debug )
printf("Unknown %s magic %#x %#o\n", KERNEL_FILE,
ex.a_magic, ex.a_magic );
# endif /* DEBUGSW defined */
return( FALSE ); /* (bad magic falls here too) */
}
pos = off + base - data;
# ifdef DEBUGSW
if( sw_debug )
printf("read_vmunix: pos %#x off %#x base %#x data %#x\n",
pos, off, base, data );
# endif /* DEBUGSW defined */
if( lseek( f, pos, 0 ) == pos && /* seek to position */
read( f, str, len ) == len ) { /* and read bytes */
close( f ); /* ok!! */
return( TRUE ); /* return good status */
} /* lseek and read OK */
close( f );
return( FALSE );
} /* read_vmunix */
# else /* COFF defined */
/*
* BSD systems using COFF end up here
* ie; DECstation3100 and Sun 386i
*
* *TODO* needs work!
*/
# include <stdio.h>
# include <filehdr.h>
# include <syms.h> /* works for DS3100. 386i?? */
# include <ldfcn.h>
# ifndef ISCOFF
/* UGH! This happens only on Umax 4.3 */
# define ISCOFF(m) ((m) >= 0500 && (m) <= 0577)
# endif /* ISCOFF not defined */
GLOBAL BOOL
read_vmunix( file, off, str, len ) /* Hacking cough... */
char *file; /* file name */
long off; /* virtual address */
char *str; /* dest buffer */
int len; /* chars to read */
{
LDFILE *ld;
# ifdef DEBUGSW
if( sw_debug )
printf("read_vmunix('%s', %x, ... , %d)\n", file, off, len );
# endif /* DEBUGSW defined */
if( (ld = ldopen(file, NULL)) == NULL )
return( FALSE );
for( ; ; ) { /* bogus loop */
if( !ISCOFF( HEADER(ld).f_magic ) )
break;
# ifdef DEBUGSW
if( sw_debug )
puts("got here");
# endif /* DEBUGSW defined */
/* more good stuff here! */
break; /* break bogus loop! */
} /* bogus for loop */
ldclose( ld );
return( FALSE );
} /* read_vmunix */
# endif /* COFF defined */
# endif /* Umax != 42 && !defined(USG) */
/*
* Local variables:
* comment-column: 40
* End:
*/