#include <sys/param.h> #include <sys/types.h>
caddr_t phystokv(paddr_t paddr); paddr_t kvtophys(caddr_t vaddr);
The phystokv( ) macro converts a physical address to a kernel virtual address. The kvtophys( ) macro converts a kernel virtual address to a physical address.
If kvtophys( ) is given a virtual address that does not map to a physical address, the kernel panics with the following message:
svirtophys - Page not present
phystokv( ) and kvtophys( ) are not the inverse of each other, because many virtual addresses may map to the same physical address. kvtophys( ) uses the page tables while phystokv( ) relies on the kernel having physical memory mapped directly in a portion of its address space, applying a simple offset to obtain the virtual address.
Up to 512MB of the kernel's virtual address space is devoted to a mapping of physical memory. With smaller memory configurations, this allows for a simple conversion between physical addresses and kernel virtual addresses. With very large physical memory configurations, however, the kernel may not have enough virtual space to map all of the physical memory. When this happens, phystokv( ) operates only on the memory that happens to be mapped. The standard driver interfaces (such as the I/O entry point routines and the memory allocation functions) handle this condition for the driver.
Drivers that need to translate between physical addresses and kernel virtual addresses should call the sptalloc(D3oddi) function to explicitly assign a kernel virtual address to the physical memory before calling phystokv( ) to ensure that the results will be valid for all memory configurations.
The result of these macros should always be cast to an explicit type. There is no compile-time parameter type checking for the phystokv( ) and kvtophys( ) macros and the return value of these macros has the same type as the parameter. If the parameter is not of a suitable type (such as if the parameter is a short or int ), and the result is not type cast, these macros silently return the wrong value.
caddr_t ptok(paddr_t paddr); paddr_t ktop(caddr_t vaddr);All drivers written for SCO OpenServer should use the phystokv( ) and kvtophys( ) macros instead.
Beginning with ODDI version 4 (SCO OpenServer Release 5.0.4), compile-time parameter type checking is enforced and these macros return a pointer type. Drivers that specify the types as documented above should work correctly in either case, but some drivers that have depended on the lax typing may have problems beginning with SCO OpenServer Release 5.0.4.
ODDI version 4 (SCO OpenServer Release 5.0.4) modified the behavior of phystokv( ) so that many drivers that are built on SCO OpenServer Release 5.0.4 cannot run on SCO OpenServer 5 Release 5.0.2 and earlier releases. SCO OpenServer Release 5.0.5 corrects this problem. Customers who want to develop drivers on SCO OpenServer Release 5.0.4 and later versions that can run on earlier releases of the operating system should preceed the #include line for the sys/immu.h header file with the following:
paddris not visable to DDI 8 drivers, so direct conversion between physical and virtual addresses is not possible.
For DDI drivers, physical requirements for allocated memory are specified through a physreq(D4) structure, which is used with memory allocation functions such as kmem_alloc_physreq(D3) and msgphysreq(D3str).
``Memory allocation'' in HDK Technical Reference