[comp.os.msdos.programmer] point to an address above 1M ?

gb7@prism.gatech.EDU (Joe Bradley) (09/24/90)

Can someone tell me how to set a pointer (in MS C) to an address above
1M? I have a video card which maps its video RAM into the PC address
space from 8M - 10M. I want to access video RAM directly, but I can't
initialize a pointer to this address range presumably because I only
have 16 bits of addressability with the segment portion of a huge pointer.
I don't see how you can point to a physical address above FFFF:FFFF ?!
I tried the following, but the compiler gives the error: "Constant too big."

#define VIDEO_BASE 0x800000000

main() {
    unsigned char huge *ram_p;

    ram_p = ( unsigned char huge * )VIDEO_BASE;
}

stever@Octopus.COM (Steve Resnick ) (09/25/90)

In article <14016@hydra.gatech.EDU> gb7@prism.gatech.EDU (Joe Bradley) writes:
>
>Can someone tell me how to set a pointer (in MS C) to an address above
>1M? I have a video card which maps its video RAM into the PC address
>space from 8M - 10M. I want to access video RAM directly, but I can't
>initialize a pointer to this address range presumably because I only
>have 16 bits of addressability with the segment portion of a huge pointer.
>I don't see how you can point to a physical address above FFFF:FFFF ?!
>I tried the following, but the compiler gives the error: "Constant too big."
>
>#define VIDEO_BASE 0x800000000
>
>main() {
>    unsigned char huge *ram_p;
>
>    ram_p = ( unsigned char huge * )VIDEO_BASE;
>}

You can't do that without entering protected mode, or by some "hidden" 
paging hardware on the video card. The FFFF:FFFF address is the top limit
on a far pointer. That address cannot be reached, normally, unless the A20
line is activated. 

Hope this helps....
Steve

-- 
----------------------------------------------------------------------------
steve.resnick@f105.n143.z1@FIDONET.ORG #include<std_disclaimer.h>
Flames, grammar errors, spelling errrors >/dev/nul
----------------------------------------------------------------------------

willis@cs.tamu.edu (Willis Marti) (09/26/90)

Let's see, the Intel architecture says segment:offset is actually
segment << 4 + offset, so:

raymond@math.berkeley.edu	kdq@demott.COM
FFFF:FFFF is   FFFF0		F000:FFFF is  F0000
              + FFFF			     + FFFF
              -----			     ------
              10FFEF			      FFFFF

Second form looks lots more correct to me.

stever@Octopus.COM (Steve Resnick ) (09/26/90)

In article <609@demott.COM> kdq@demott.COM (Kevin D. Quitt) writes:
>In article <1990Sep24.204400.26052@Octopus.COM> stever@Octopus.COM (Steve Resnick ) writes:
>>In article <14016@hydra.gatech.EDU> gb7@prism.gatech.EDU (Joe Bradley) writes:
>>>
>>>Can someone tell me how to set a pointer (in MS C) to an address above
>>>1M? 
>
>>paging hardware on the video card. The FFFF:FFFF address is the top limit
>
>    Picking a nit, to be sure, but the highest address is *not* FFFF:FFFF,
>it is F000:FFFF (or FF00:0FFF, or FFF0:00FF, or FFFF:000F).

Well, sort of... FFFF:FFFF is the highest address a 32bit pointer will access
is it is used in the conventional DOS style addressing. If the A20 line is
enabled and there is an additional 62K above 1M the 0xFFFFFFFF pointer should
access the top of this RAM. You are, however, correct, Kevin, when you
say that F000:FFFF is the top limit for an 8086(8) and 80186(8) processors.

I love picking nits! :)

Cheers! 
Steve

-- 
----------------------------------------------------------------------------
steve.resnick@f105.n143.z1.FIDONET.ORG - or - apple!camphq!105!steve.resnick
Flames, grammar errors, spelling errrors >/dev/nul
----------------------------------------------------------------------------

marcb@hp-ptp.HP.COM (Marc Brandis) (09/26/90)

A clarification to the following postings.

>>    Picking a nit, to be sure, but the highest address is *not* FFFF:FFFF,
>>it is F000:FFFF (or FF00:0FFF, or FFF0:00FF, or FFFF:000F).
>
>Picking another nit, the highest address *is* FFFF:FFFF, not F000:FFFF
>(or its equivalent forms).  But in order to access memory above
>FFFF:000F, you have to play with the A20 line.  Use the HIMEM.SYS
>device driver to do this in a manner compatible with other programs.


>    Just how do you pack your 32 bit address into 21 address lines?

Address translation on all Intel processors in real mode works as
follows: The CPU shifts the segment part of the address 4 bits to the
left (multiplies it by 16) and then adds the offset part to it,    
resulting in a 20 bit physical address. Of course, when you specify
a combination of segment and offset like FFFF:FFFF, the result over-
flows into the next higher bit, yielding a 21 bit address. The 8088,
8086, 80188 and 80186 have only 20 address lines, so the highest bit
is just ignored, so that all addresses still lie in the first megabyte.
However, the 80286, 80386 and 80486 have more than 21 address lines,
and there the 21st address bit is set in this case, causing the CPU
to access memory above the first megabyte. For compatibility reasons,
all systems based on the 286, 386 and 486 include special circuitry,
that causes this address line (A20) to be zero. This "feature" can
be disabled, so that nearly 64k more memory becomes addressable in
real mode. And that is exactly what HIMEM.SYS does.


(* I speak only for myself.
	Marc-Michael Brandis
	Institut fuer Computersysteme
	ETH Zentrum
	CH-8092 Zuerich, Switzerland
	e-mail: brandis@inf.ethz.ch
		brandis@iis.ethz.ch
   Temporarily at HP, marcb@hp-ptp.ptp.hp.com
*)

m912208@usna.NAVY.MIL (Midn. John W. Fancher) (09/28/90)

In article <1990Sep24.204400.26052@Octopus.COM> steve.resnick@f105.n143.z1.FIDONET.ORG writes:
>In article <14016@hydra.gatech.EDU> gb7@prism.gatech.EDU (Joe Bradley) writes:
>>
>>Can someone tell me how to set a pointer (in MS C) to an address above
>>1M? I have a video card which maps its video RAM into the PC address
>>space from 8M - 10M. I want to access video RAM directly, but I can't
>>initialize a pointer to this address range presumably because I only
>>have 16 bits of addressability with the segment portion of a huge pointer.
>>I don't see how you can point to a physical address above FFFF:FFFF ?!
>>I tried the following, but the compiler gives the error: "Constant too big."
>>
>>#define VIDEO_BASE 0x800000000
>>
>>main() {
>>    unsigned char huge *ram_p;
>>
>>    ram_p = ( unsigned char huge * )VIDEO_BASE;
>>}
>
>You can't do that without entering protected mode, or by some "hidden" 
>paging hardware on the video card. The FFFF:FFFF address is the top limit
>on a far pointer. That address cannot be reached, normally, unless the A20
>line is activated. 

   There is another way to get that high into extended memory space (
above 1M).
  
   I am assuming that you have a 286 based machine. (Since if you have 
a 386 then the problem is just a matter of using the chips 
extended memory mapping capabilities which is documented quite well.)

   First off, there is an "undocumented" instruction on the 286 called
LOADALL.  It was probably included for use for INTEL to test the chip
at the factory.  It has the special ability to, in one instruction, set
every single register on the 286, even some that you didn't know existed.
To say the least, it is a very complicated touchy problem.  It requires
setting up a table for this instruction to read and do the appropriate
changes to the chip.  

   The important part of this instruction is that it gives you access to 
the segment register discriptor cache registers.  These registers actually
define what PHYSICAL address (full 24 bit) the segment registers really 
want to look at.  When you load the DS segment register with an address, the
address is expanded to 24 bits and copied to the SRDCs.  Since with the 
LOADALL instruction you can change these SRDCs independent of the segment
registers then you can tell them to point anywhere in the 16M addressing
space of the 286.  

    However, there are more pitfalls to using this method than you can wave
a floppy disk at.  These are too numerous to list here.  These problems 
have nothing to do with being or not being in protected mode.  This method
can be used in real mode or protected mode equally.  

    There is a company that has software libraries and documentation for
sale and some at a shareware type of deal to entice you to get the whole
package.  
	The company is:

			Semi-Intelligent Systems
				PO BOX 4492
			ALBUQUERQUE, NM 87196

    They produce the HYPER-SPACE NAVIGATOR'S GUIDE which talks about all
sorts of neat tricks of using LOADALL and accessing extended memory.  The
last I remember the whole book and included software cost about $40-$50.


I hope this helps....

John W. Fancher

----------------------------------------------------------------------------
--	Me?  I said that?  You must be joking.  I can't even balance my   --
--	checkbook.                                                        --
----------------------------------------------------------------------------