HP3000-L Archives

November 2001, Week 3

HP3000-L@RAVEN.UTC.EDU

Options: Use Monospaced Font
Show Text Part by Default
Show All Mail Headers

Message: [<< First] [< Prev] [Next >] [Last >>]
Topic: [<< First] [< Prev] [Next >] [Last >>]
Author: [<< First] [< Prev] [Next >] [Last >>]

Print Reply
Subject:
From:
Stan Sieler <[log in to unmask]>
Reply To:
Stan Sieler <[log in to unmask]>
Date:
Sat, 17 Nov 2001 13:33:13 -0800
Content-Type:
text/plain
Parts/Attachments:
text/plain (87 lines)
Re:
> Is there a simple way to check an address in a 'c' program to see that is
> in my address space and will not cause a TRAP65 'Invalid data address' when
> passed to a system routine (like _doprnt)?

Good question :)

There's probably no *simple* way  ... that's one of the things
I'd asked for when I proposed a memory manager API some years ago.

There are three basic reasons an address might trap:

   1) it isn't properly aligned:

      - it isn't 8-byte aligned, but the code expected it to be (e.g.,
      code is doing quad load/store)

      - it isn't 4-byte aligned, but the code expected it to be (e.g.,
      code is doing LDW or STW)

      - it isn't 2-byte aligned, but the code expected it to be (e.g.,
      code is doing LDH or STH)

      This you can check for ahead of time, by checking the bottom one, two
      or three bits of the address.

   2) it's a valid address, but secured so that you can't access it
      from the ring level you are running at (e.g., OS data)

      This can be checked, in user mode, by using the PROBER or PROBEW
      instructions.  IIRC, there are ways of emitting this instruction from
      both C/ix and gcc, but I can't recall them just now.  The Pascal and
      SPLash! compilers both have constructs to emit those
      instructions.

   3) the address is "bad" (isn't a valid/allocated virtual address)

      The OS has several routines, which require priv mode access to use,
      that can check a virtual address.  (e.g., probe_t ())

With Pascal, I can check the second and third cases:

   $standard_level 'os_features'$
   $type_coercion 'representation'$
   $subprogram$

   function  is_address_readable (ptr : localanyptr) : boolean;

      type
         char_ptr_type = ^ char;

      var
         c : char;

      begin

      try
         begin
         c := char_ptr_type (ptr)^;     {NOTE: may cause a trap!}
         is_address_readable := true;
         end

      recover
         is_address_readable := false;

      end {is_address_readable proc};

Note that I wouldn't use this code if I expected it would be called
a *lot* (thousands of times) *and* there was a fairly good probability
that the address might be bad.  I.e., trapping isn't cheap ... it
takes about 3 milliseconds on an HP 3000/968.

If you have Pascal, you can compile that and link it into your C program
and use it:

   extern int is_address_readable (char *c);

   ...
   if (! is_address_readable (&foo))
      QUIT (101);

Stan Sieler                                           [log in to unmask]
www.allegro.com/sieler/wanted/index.html          www.allegro.com/sieler

* To join/leave the list, search archives, change list settings, *
* etc., please visit http://raven.utc.edu/archives/hp3000-l.html *

ATOM RSS1 RSS2