Previous | Contents | Index |
For more information about the image segment synopsis section of a map file, see Chapter 5.
To find out which sections the linker placed in each segment, look at the Program Section Synopsis section of the map file. This section lists all the sections in each cluster and lists the contributions (the number of bytes) to each section from each object module. By comparing the base address of the sections with the base address of the segments in the Image Segment Synopsis section, you can tell in which segment the sections appear. Example 3-7 is an excerpt from the Program Section Synopsis section of the map file produced by the sample link operation (Example 3-5).
Example 3-7 Section Information in a Map File |
---|
+--------------------------+ ! Program Section Synopsis ! +--------------------------+ Psect Name Module/Image Base End Length Attributes (1) ---------- ------------ ---- --- ------ ---------- GLOBAL_DATA 00010000 00010003 00000004 ( 4.) NOEXE, WRT MYSUB 00010000 00010003 00000004 ( 4.) Initializing Contribution SUB_DATA 00010010 00010013 00000004 ( 4.) NOEXE, WRT MYSUB 00010010 00010013 00000004 ( 4.) Initializing Contribution $CODE$ 00020000 0002008F 00000090 ( 144.) EXE,NOWRT MYSUB 00020000 0002006F 00000070 ( 112.) <Linker> 00020070 0002008F 00000020 ( 32.) $LITERAL$ 00030000 0003000C 0000000D ( 13.) NOEXE,NOWRT MYSUB 00030000 0003000C 0000000D ( 13.) $LINKER UNWIND$ 00040000 00040017 00000018 ( 24.) NOEXE,NOWRT MYSUB 00040000 00040017 00000018 ( 24.) $LINKER UNWINFO$ 00040018 0004002F 00000018 ( 24.) NOEXE,NOWRT MYSUB 00040018 0004002F 00000018 ( 24.) ADD_DATA 00050000 00050003 00000004 ( 4.) NOEXE, WRT MYADD 00050000 00050003 00000004 ( 4.) Initializing Contribution $CODE$ 00060000 000602CF 000002D0 ( 720.) EXE,NOWRT MYTEST 00060000 000601BF 000001C0 ( 448.) MYADD 000601C0 0006022F 00000070 ( 112.) <Linker> 00060230 000602CF 000000A0 ( 160.) $LITERAL$ 00070000 0007003C 0000003D ( 61.) NOEXE,NOWRT MYTEST 00070000 00070027 00000028 ( 40.) MYADD 00070030 0007003C 0000000D ( 13.) $LINKER UNWIND$ 00080000 00080047 00000048 ( 72.) NOEXE,NOWRT MYTEST 00080000 0008002F 00000030 ( 48.) MYADD 00080030 00080047 00000018 ( 24.) $LINKER UNWINFO$ 00080048 000800A7 00000060 ( 96.) NOEXE,NOWRT MYADD 000601C0 0006022F 00000070 ( 112.) <Linker> 00060230 000602CF 000000A0 ( 160.) $LITERAL$ 00070000 0007003C 0000003D ( 61.) NOEXE,NOWRT MYTEST 00070000 00070027 00000028 ( 40.) MYADD 00070030 0007003C 0000000D ( 13.) $LINKER UNWIND$ 00080000 00080047 00000048 ( 72.) NOEXE,NOWRT MYTEST 00080000 0008002F 00000030 ( 48.) MYADD 00080030 00080047 00000018 ( 24.) $LINKER UNWINFO$ 00080048 000800A7 00000060 ( 96.) NOEXE,NOWRT MYTEST 00080048 0008008F 00000048 ( 72.) MYADD 00080090 000800A7 00000018 ( 24.) $LINKER SDATA$ 00090000 000900B7 000000B8 ( 184.) NOEXE,NOWRT,SHORT <Linker> 00090000 000900B7 000000B8 ( 184.) |
For more information about the Program Synopsis Section of a map file,
see Section 5.2.4.
3.3.5 Allocating Memory for Segments
When it creates a segment, the linker allocates enough memory for the image segment to accommodate all the sections it contains. Each section definition includes its size.
The linker aligns segments on CPU-specific page boundaries. Within a segment, the linker assigns to each section a virtual address relative to the base address of the segment.
If the sections have the concatenated (CON) attribute set, the linker positions the sections one after the other within a segment, inserting padding bytes between the sections if necessary to achieve the alignment requirement of a particular contribution to a section. The linker retains the alignment specified for each section contribution but uses the largest alignment of a contributing module as the alignment of the whole section.
With a PSECT_ATTR= option you can align the section within the segment. However, aligning the section does not influence the alignment of the individual contributions to the section. The linker follows the compiler's alignment specification when it aligns each individual contribution. If you specify a smaller alignment for a section than any compiler-assigned alignment from all contributions, the linker issues a warning.
If the sections have the overlaid (OVR) attribute set, the linker uses the same start address for the sections so that they occupy the same virtual memory (that is, the sections overlay each other). For overlaid sections, the linker allocates enough space to accommodate the largest of all the section contributions. Note that the linker does not generate a warning message if the contributions specify different size allocations.
Any module can initialize the contents of an overlaid program section. However, the I64 linker only allows compatible initializations for the same section data. See Section 3.4.1 for an explanation of a compatible initialization.
The linker allocates virtual memory to all the segments beginning at a page size boundary. The linker usually places segments in the P0 region. It currently uses a default page size of 10000 hexadecimal, which is an architecture specific value. However, you can specify the page size using the /BPAGE qualifier. (For information about the /BPAGE qualifier, see Part 4.)
By default, the first P0 segment is placed at 10000 hexadecimal, leaving the first page unused as a guard page. The first P2 segment (for example containing sections with the ALLOC_64BIT attribute) is placed at 80000000 hexadecimal. However, all segment base addresses are only suggestions for the OpenVMS image activator. The image activator can determine a different base address for each segment (within the address region) to map the segment. This is always the case for shareable images. This is also the case for all images being installed as resident images, where the INSTALL utility determines the addresses. Unlike the Alpha and VAX platforms, executable images can also have their segment base addresses determined by the image activator or the INSTALL utility.
An image not activated by the OpenVMS image activator might need a specific base address for the first segment. For such an image, you can specify this address with the /BASE_ADDRESS qualifier. (For information about the /BASE_ADDRESS qualifier, see Part 4.)
Because the linker processes clusters in the order in which they appear in the cluster list, the virtual address space of the final image will generally contain contiguous segments of consecutive clusters on the basis of their order in the cluster list.
After allocating memory for all segments in a cluster, the linker relocates their contents by performing the following processing:
When it creates segments, the linker assigns attributes to the segment based on the attributes of the sections it contains. The segment attributes describe certain characteristics of the portion of memory they represent, for example, the protection characteristics. For example, a segment that contains sections with the writability attribute also has the writability attribute set. Table 3-4 and Table 3-5 include the segment attributes associated with a segment that contains sections with a particular set of attributes. Table 3-7 lists all the segment attributes. Segment attributes, like section attributes, are Boolean values that are either on or off.
Attribute | Symbol1 | Function |
---|---|---|
Executability | PF_X | The mapping of the EXE attribute from the section. |
Write | PF_W | The mapping of the WRT attribute from the section. |
Readability | PF_R | All segments have this attribute set. |
Modified if Relocated | PF_VMS_NOWRIT_RELOC | The attribute is set by the linker if the the segment contents is changed when relocated. The image activator sets the protection to NOWRT after the relocation. |
Initial Code | PF_VMS_INITALCODE | This attribute is reserved by HP. |
Resident | PF_VMS_RESIDENT | This attribute is reserved by HP. |
Vectored | PF_VMS_VECTOR | The mapping of the VEC attribute from the section. |
Protected | PF_VMS_PROTECT | Protect indicates that a section is protected. The linker sets the PF_VMS_PROTECT attribute whenever PF_VMS_VECTOR is set. PROTECT is also set if the /PROTECT qualifier is used, or if the cluster that the segment is spawned from came after a PROTECT=YES option (and before a PROTECT=NO option). |
Modified by Fix-Ups | PF_VMS_NOWRIT_FIXUP | The attribute is set by the linker if the segment contents is changed for fix-ups. The image activator sets the protection to NOWRT after the fix-ups are applied. |
Short Data | PF_VMS_SHORT | The mapping of the SHORT attribute from the section. |
Shared | PF_VMS_SHARED | The SHR mapping of the SHR attribute from the sections. |
The Image Segment Synopsis section of a map file lists the attributes of each segment created in the Protection and Attributes columns. See Example 3-6 for an illustration and see Table 3-3 for the display names in these columns. You can also get a listing of all the segments created by the linker by using the ANALYZE/IMAGE utility. The output generated by this utility includes a list of all the segments that make up the image, with their attributes. An excerpt from the analysis of the image file MYTEST.EXE is shown in Example 3-8.
Example 3-8 Image Segment Descriptions in an ANALYZE/IMAGE Display |
---|
SEGMENT HEADER ENTRY 0. Offset Description Hex (<bitmask>) Interpretation ------ ----------- --------------- -------------- 00000000 Segment Type: 00000001 PHDR$K_PT_LOAD 00000004 Segment Flags: 00000006 (1) Segment is writeable: <00000002> PHDR$M_PF_W Segment is readable: <00000004> PHDR$M_PF_R 00000008 Offset to Segment Data: 0000000000000400 (2) 00000010 Memory Virtual Address: 0000000000010000 (3) 00000018 Page Fault Cluster Size: 0000000000000000 (4) 00000020 Segment Size in File: 0000000000000014 (5) 00000028 Segment Size in Memory: 0000000000000014 (6) 00000030 Alignment Constraint: 0000000000000010 SEGMENT HEADER ENTRY 1. (0001) 56. (0038) bytes Offset Description Hex (<bitmask>) Interpretation ------ ----------- --------------- -------------- 00000000 Segment Type: 00000001 PHDR$K_PT_LOAD 00000004 Segment Flags: 00000005 (1) Segment is executable: <00000001> PHDR$M_PF_X Segment is readable: <00000004> PHDR$M_PF_R 00000008 Offset to Segment Data: 0000000000000600 (2) 00000010 Memory Virtual Address: 0000000000020000 (3) 00000018 Page Fault Cluster Size: 0000000000000000 (4) 00000020 Segment Size in File: 0000000000000090 (5) 00000028 Segment Size in Memory: 0000000000000090 (6) 00000030 Alignment Constraint: 0000000000000010 . . . |
The items in the following list correspond to the numbers in Example 3-8:
You can control how the linker combines sections into segments in the following ways:
The linker combines sections in the same cluster into the same segment if they have the same settings for the significant section attributes. To force the linker to put the sections into different segments, change the attributes of one of the sections by using the PSECT_ATTR= option.
For example, in the sample link operation, the GLOBAL_DATA section has the WRT attribute. But its contents, the variable global_data, serves as a constant (initialized but never changed). If you want the GLOBAL_DATA section to appear in a read-only segment, change the writability attribute. For example, in the following link of the sample programs, the writability attribute is set to NOWRT.
$ LINK/MAP/FULL MYTEST,MYADD,SYS$INPUT/OPT CLUSTER=MYSUB_CLUS,,,MYSUB PSECT_ATTR=GLOBAL_DATA,NOWRT [Ctrl/Z] |
Example 3-9 shows the image and program section synopsis for the second link.
Example 3-9 Image and Program Section Synopsis of Second Link |
---|
+--------------------------+ ! Program Section Synopsis ! +--------------------------+ Psect Name Module/Image Base End Length Attributes ---------- ------------ ---- --- ------ ---------- SUB_DATA 00010000 00010003 00000004 ( 4.) NOEXE, WRT,NOVEC, MOD MYSUB 00010000 00010003 00000004 ( 4.) Initializing Contribution $CODE$ 00020000 0002008F 00000090 ( 144.) EXE,NOWRT,NOVEC, MOD MYSUB 00020000 0002006F 00000070 ( 112.) <Linker> 00020070 0002008F 00000020 ( 32.) $LITERAL$ 00030000 0003000C 0000000D ( 13.) NOEXE,NOWRT,NOVEC, MOD MYSUB 00030000 0003000C 0000000D ( 13.) GLOBAL_DATA 00030010 00030013 00000004 ( 4.) NOEXE,NOWRT,NOVEC, MOD MYSUB 00030010 00030013 00000004 ( 4.) Initializing Contribution $LINKER UNWIND$ 00040000 00040017 00000018 ( 24.) NOEXE,NOWRT,NOVEC, MOD MYSUB 00040000 00040017 00000018 ( 24.) . . . |
Note that there is no change in the number and attributes of the
segments. However, the GLOBAL_DATA section moved into an existing
read-only segment. (It also moved in the address space.) The
GLOBAL_DATA section is now in the same segment as the read-only
$LITERAL$ section, which it follows, based on alphabetical order (for a
comparison, see Example 3-7).
3.3.7.2 Alternate Way to Modify Section Attributes
With the /SEGMENT_ATTRIBUTE qualifier, you can change some attributes for a class of sections. The keywords SHORT_DATA, CODE, and SYMBOL_VECTOR define obvious classes of sections: all sections with the SHORT, all sections with the EXE attribute, and the symbol vector section. The attribute to change depends on the class.
For short data sections, you can set WRT. For executable sections, you can set or clear the ALLOC_64BIT attribute. For the symbol vector, you can set or clear the SHORT attribute. To be compatible with other DCL command qualifiers, for the first two classes, more descriptive names are used: WRITE for WRT, P0 for NOALLOC_64BIT, P2 for ALLOC_64BIT. (For information about the /SEGMENT_ATTRIBUTE qualifier, see the Command Reference in Part 4.)
With /SEGMENT_ATTRIBUTE, the section attributes are changed before the sections are collected into segments. As a result, the effect is the same as using the PSECT_ATTR= for each member of the class. However, /SEGMENT_ATTRIBUTE can do more because even the linker-generated sections are members of the classes (for example, $LINKER SDATA$ and $LINKER SYMBOL_VECTOR$).
To move all code into P2 space, you can use the /SEGMENT_ATTRIBUTE=CODE=P2 command qualifier. Please note, that if you use clusters in the same link command (with linker options) and if EXE sections are put on specific clusters, setting ALLOC_64BIT does not change the per cluster segment creation. You then will see more than one executable segment with base addresses in P2 space.
The /SEGMENT_ATTRIBUTE=SHORT_DATA=WRITE command qualifier allows you to combine the read-only and the read-write short data segments into a single segment, reclaiming up to 65,535 bytes of unused, read-only space (default value for /BPAGE). When setting SHORT_DATA to WRITE, your program may accidentally write to formerly read-only data. Therefore, this qualifier is recommended only if your short data segment has reached the limit of 4 MB.
By default, the linker stores the shareable image's symbol vector into
the read-only short data segment. That is, the linker created section
$LINKER SYMBOL_VECTOR$ has the SHORT attribute. By specifying
/SEGMENT_ATTRIBUTE=SYMBOL_VECTOR=NOSHORT, the linker clears the SHORT
attribute of the section and, therefore, collects the symbol vector
into a read-only data segment of the default cluster. If the shareable
image has no read-only data se is created. This frees up the symbol
vector entries from the short data. This qualifier is recommended only
if your short data segment has reached the limit of 4 MB.
3.3.7.3 Manipulating Cluster Creation
In general, the linker creates segments on a per-cluster basis; that is, only sections within a particular cluster can contribute to segment creation. (The linker can collect sections with the global attribute from all clusters into a single segment. However, there is one expection: sections with the SHORT attribute can not be collected.) To ensure that a section appears in a particular segment, put the section in a specific cluster.
For example, in the sample link operation illustrated in Example 3-5, the linker puts all the sections in the object module MYSUB.OBJ in the cluster named MYSUB_CLUS because the CLUSTER= option is specified. If you wanted to group all of the sections that contain code from all the other clusters into the MYSUB_CLUS cluster, you could specify the COLLECT= option, as in the following example.
Section naming conventions are language processor specific. By convention, most OpenVMS language processors put the code they generate into sections named $CODE$. An exception is the HP C++ compiler which puts code into a section named .text . |
$ LINK/MAP/FULL MYTEST, MYADD, SYS$INPUT/OPT CLUSTER=MYSUB_CLUS,,,MYSUB COLLECT=MYSUB_CLUS,$CODE$ [Ctrl/Z] |
Previous | Next | Contents | Index |