QUARTLY-REVENUE OCCURS 4 TIMES PIC 9(7)V99. Will allocate the following: QUARTLY-REVENUE (1) QUARTLY-REVENUE (2) QUARTLY-REVENUE (3) QUARTLY-REVENUE (4)
05 QUARTLY-REVENUE OCCURS 4 TIMES PIC 9(7)V99. Will allocate the following: QUARTLY-REVENUE (1) QUARTLY-REVENUE (2) QUARTLY-REVENUE (3) QUARTLY-REVENUE (4)
Each occurrence is referenced using the subscript syntax (a numeric literal, arithmetic expression or numeric identifier enclosed within parenthesis) shown in the diagram. The OCCURS clause may be used at the group level too, in which case the entire group structure repeats, as follows:
12 Other programming languages with which you might be familiar refer to this sort of structure as an array.
05 X OCCURS 3 TIMES. 10 A PIC X(1). 10 B PIC X(1). 10 C PIC X(1).
C (3) See sections 6.1.1 (Table References), 6.38 (SEARCH), 6.40 (SORT) as well as item # 28 below for more information
B (3)
about tables.
13. The optional DEPENDING ON clause can be added to an OCCURS to create a variable-length table. Such tables will
be allocated out to the maximum size specified as integer-2. At execution time the value of identifier-5 will determine how many of the table elements are accessible.
14. The OCCURS clause cannot be specified in a data description entry that has a level number of 01, 66, 77, or 88.
15. VALUE specifies an initial compilation-time value that will be assigned to the storage occupied by the data item in the program object code generated by the compiler. If the optional “ALL” clause is used, it may only be used with an alphanumeric literal value; the value will be repeated as needed to completely fill the data item. Here are
some examples with and without ALL: PIC X(5) VALUE “A” – will have the value “A”,SPACE,SPACE,SPACE,SPACE PIC X(5) VALUE ALL “A” – will have the value “A”,”A”,”A”,”A”,”A” PIC 9(3) VALUE 1 – will have the value 001 PIC 9(3) VALUE ALL “1” – will have the value 111
16. The ASCENDING KEY, DESCENDING KEY and INDEXED BY clauses will be discussed in section 6.39 (SEARCH).
17. The BASED and ANY LENGTH clauses cannot be used together.
18. The JUSTIFIED RIGHT clause, valid only on an alphabetic (PIC A) or alphanumeric (PIC X) item, will cause values shorter than the length of the data item to be right-justified and space-filled when they are MOVEd into the data item.
19. Data items declared with BASED are allocated no storage at compilation time. At run-time, the ALLOCATE verb is used to allocate space for and (optionally) initialize such items.
20. Data items declared with the ANY LENGTH attribute have no fixed compile-time length. Such items may only be defined in the LINKAGE SECTION as they may only serve as subroutine argument descriptions. ANY LENGTH items must have a PICTURE clause that specifies exactly one A, X or 9 symbol.
21. The BLANK WHEN ZERO clause, when used on a numeric item, will cause that item’s value to be automatically transformed into SPACES if a value of 0 is ever MOVEd to the item.
22. The REDEFINES clause causes identifier-1 to occupy the same physical storage space as identifier-2, so that storage may be defined in a different manner with a (probably) different structure. The following must all be true in order to use REDEFINES:
a. The level number of identifier-2 must be the same as that of identifier-1.
b. The level number of identifier-2 (and identifier-1) cannot be 66, 77, 78 or 88.
c. If “n” represents the level number of identifier-2 (and identifier-1), then no other data items with level
number “n” may be defined between identifier-1 and identifier-2.
d. The total allocated size of identifier-1 must be the same as the total allocated size of identifier-2.
e. No OCCURS clause may be defined on identifier-2. There may – however – be items defined with OCCURS clauses subordinate to identifier-2.
f. No VALUE clause may be defined on identifier-2. No data items subordinate to identifier-2 may have VALUE clauses, with the exception of level-88 condition names.
23. The following table summarizes the various possible USAGE specifications: Figure 5-10 - Summary of USAGE Specifications
Used USAGE
Storage
Allows
Allocated Space (Bytes)
Identical To
Depends on number of “9”s in PICTURE
Most-compatible If PICTURE Yes
COMPUTATIONAL,
and the ”binary-size” setting of the
– see # 24 contains
COMPUTATIONAL-4
configuration file (section 7.1.8 ) used to
“S”
compile the program
BINARY-CHAR or
One byte
Native – see # 24 Yes
No
BINARY-CHAR SIGNED BINARY-CHAR UNSIGNED
One byte
Native – see # 24 No – see
No
BINARY-C-LONG or
Allocates the same amount of storage as
Native – see # 24 Yes
No
BINARY-C-LONG SIGNED
does the C language “long” data type on that computer; typically this is 32 bits but it could be 64 bits
BINARY-C-LONG UNSIGNED
Allocates the same amount of storage as
Native – see # 24 No – see
No
does the C language “long” data type on
that computer; typically this is 32 bits but it could be 64 bits
BINARY-DOUBLE or
Allocates a “traditional” double-word of
Native – see # 24 Yes
No
BINARY-DOUBLE SIGNED
storage (64 bits)
BINARY-DOUBLE UNSIGNED
Allocates a “traditional” double-word of
Native – see # 24 No – see
No
storage (64 bits)
BINARY-LONG or
SIGNED-LONG, BINARY-LONG SIGNED
Allocates a word of storage (32 bits)
Native – see # 24 Yes
No
SIGNED-INT BINARY-LONG UNSIGNED
Allocates a word of storage (32 bits)
Native – see # 24 No – see
No
UNSIGNED-LONG, # 25 UNSIGNED-INT
BINARY-SHORT or
SIGNED-SHORT BINARY-SHORT SIGNED
Allocates a half-word of storage (16 bits)
Native – see # 24 Yes
No
BINARY-SHORT UNSIGNED
Allocates a half-word of storage (16 bits)
Native – see # 24 No – see
Depends on number of “9”s in PICTURE
Most-compatible If PICTURE Yes
BINARY, COMPUTATIONAL-4
and the ”binary-size” setting of the
– see # 24 contains
configuration file (section 7.1.8) used to
“S”
compile the program
COMPUTATIONAL-1
Allocates a word of storage (32 bits)
Allocates a double-word of storage (64
Double-precision Yes
Allocates 4 bits per “9” in the PICTURE
Packed decimal – If PICTURE No
PACKED-DECIMAL
plus a (trailing) 4-byte field for the sign,
see # 26 contains
rounded up to the nearest byte,
“S”
SYNCHRONIZED RIGHT (see # 27 )
COMPUTATIONAL-4
Depends on number of “9”s in PICTURE
Most-compatible If PICTURE Yes
BINARY, COMPUTATIONAL
and the ”binary-size” setting of the
– see # 24 contains
configuration file (section 7.1.8) used to
“S”
compile the program
COMPUTATIONAL-5
Depends on number of “9”s in PICTURE
If PICTURE Yes
and the ”binary-size” setting of the
contains
configuration file (section 7.1.8 ) used to
“S”
compile the program
Allocated Space (Bytes)
Identical To
Allocates bytes based upon the number
Most-compatible If PICTURE Yes
of “9”s in the PICTURE according to the
– see # 24 contains
”binary-size” setting of “1—8” in the
“S”
configuration file used to compile the program. See section 7.1.8 for an illustration of how a value of “1—8” for “binary-size” would work.
DISPLAY
Depends on PICTURE – One character 13 Characters
If PICTURE Yes
per X, A, 9, period, $, Z, 0, *, S (if
contains
SEPARATE CHARACTER specified), +, - or
“S”
B symbol in PICTURE; Add 2 more bytes if DB or CR symbol used
INDEX
Allocates a word of storage (32 bits)
Native – see # 24 No
No
NATIONAL
USAGE NATIONAL, while syntactically recognized, is not supported by OpenCOBOL
PACKED-DECIMAL
Allocates 4 bits per “9” in the PICTURE
Packed decimal – If PICTURE No
COMPUTATIONAL-3
plus a (trailing) 4-byte field for the sign,
see # 26 contains
rounded up to the nearest byte,
“S”
SYNCHRONIZED RIGHT (see # 27 )
POINTER
Allocates a word of storage (32 bits)
Native – see # 24 No
No
PROGRAM-POINTER
Allocates a word of storage (32 bits)
Native – see # 24 No
No
SIGNED-INT
Allocates a word of storage (32 bits)
Native – see # 24 Yes
No
BINARY-LONG-SIGNED, SIGNED-LONG
SIGNED-LONG
Allocates a word of storage (32 bits)
Native – see # 24 Yes
No
BINARY-LONG SIGNED, SIGNED-INT
SIGNED-SHORT
BINARY SHORT SIGNED UNSIGNED-INT
Allocates a half-word of storage (16 bits)
Native – see # 24 Yes
No
Allocates a word of storage (32 bits)
Native – see # 24 No – see
No
BINARY-LONG UNSIGNED, # 25 UNSIGNED-LONG
UNSIGNED-LONG
Allocates a word of storage (32 bits)
Native – see # 24 No – see
No
BINARY-LONG UNSIGNED, # 25 UNSIGNED-INT
UNSIGNED-SHORT
Allocates a half-word of storage (16 bits)
Native – see # 24 No – see
No
BINARY-SHORT UNSIGNED
24. Binary data can be stored in either a “Big-Endian” or “Little-Endian” form. Big-endian data allocation calls for the bytes that comprise a binary item to be allocated such that the least-
significant byte is the right-most byte. For example, a four-byte binary item having a value of decimal 20 would
be big-endian allocated as 00000014 (shown in hexadecimal notation). Little-endian data allocation calls for the bytes that comprise a binary item to be allocated such that the least-
significant byte is the left-most byte. For example, a four-byte binary item having a value of decimal 20 would be little-endian allocated as 14000000 (shown in hexadecimal notation).
A ll CPUs are capable of “understanding” big-endian format, which makes it the “most-compatible” form of binary storage across computer systems.
Some CPUs – such as the Intel/AMD i386/x64 architecture processors such as those used in most Windows PCs – prefer to process binary data stored in a little-endian format. Since that format is more efficient on those systems, it is referred to as the “native” binary format.
13 In t his context, one character is the same as one byte, unless you’ve built yourself an OpenCOBOL system that uses Unicode (unlikely), in which case 1 character = two bytes.
On a system supporting only one format of binary storage (generally, that would be big- endian), the terms “most- efficient” format and “native format” are synonymous.
25. Binary data items that have the UNSIGNED attribute explicitly coded, or that do not have an “S” symbol in their PICTURE clause cannot preserve negative values that may be stored into them. Attempts to store a negative value into such a field will actually result in the binary representation of the negative number actually being interpreted as if it were a positive number. For example, on a computer running an Intel or AMD processor, the
value of -3 expressed as a binary value would be 11111101 2 . If that value is moved into a USAGE BINARY-CHAR
UNSIGNED field, it would actually be interpreted as 011111101 2 , or 253.
26. Packed-decimal (i.e. USAGE COMP-3 or USAGE PACKED-DECIMAL) data is stored as a series of bytes such that each byte contains two 4- bit fields with each field representing a “9” in the PICTURE and storing a single decimal digit. The last byte will always contain a single 4- bit digit (corresponding to a “9” and a 4-bit sign indicator (always present, even if no “S” symbol is used). The first byte may contain an unused left-most 4-bit field, depending on how many “9” symbols were used in the PICTURE. The sign indicator will have a value of a hexadecimal A thru F, with values of A, C, E and F indicating a positive sign and B or D representing a negative value. Therefore, a PIC S9(3) COMP-3 packed-decimal field with a value of -15 would be stored internally as a hexadecimal 015D (or perhaps a 015B). If you attempt to store a negative number into a packed d ecimal field that has no “S” in its PICTURE, the absolute value of the negative number will actually be stored.
27. The SYNCHRONIZED clause (which may be abbreviated as SYNC) optimizes the storage of binary numeric items to store them in such a manner as to make it as fast as possible for the CPU to fetch them. This synchronization is performed as follows:
a. If the binary item occupies one byte of storage, no synchronization is performed.
b. If the binary item occupies two bytes of storage, the binary item is allocated at the next half-word boundary.
c. If the binary item occupies four bytes of storage, the binary item is allocated at the next word boundary.
d. If the binary item occupies four bytes of storage, the binary item is allocated at the next word boundary. Here’s an example of a group item’s storage allocation with and without using SYNCHRONIZED: Figure 5-11 - Effect of the SYNCHRONIZED Clause
01 Group-Item-1.
01 Group-Item-2.
05 A PIC X(1). 05 A PIC X(1). 05 B USAGE BINARY-SHORT.
05 B SYNC USAGE BINARY-SHORT. 05 C PIC X(2).
05 C PIC X(2). 05 D USAGE BINARY-LONG.
05 D SYNC USAGE BINARY-LONG. 05 E PIC X(3).
05 E PIC X(3). 05 F USAGE BINARY-DOUBLE.
05 F SYNC USAGE BINARY-DOUBLE.
½ Word Word Word Word Word Word Word Word Word Word Word Word Word
Group-Item-1 A B C D E F Group-Item-2 A B C D E F
The grey blocks represent the unused “slack” bytes that are allocated in the Group-Item-2 structure because of the SYNC clauses.
The LEFT and RIGHT options to the SYNCHRONIZED clause are recognized for syntactical compatibility with other COBOL implementations, but are otherwise non-functional.
28. Initializing a table is one of the trickier aspects of COBOL data definition. There are basically three standard techniques and a fourth that people familiar with other COBOL implementations but new to OpenCOBOL may find interesting . So, here are the three “standard” approaches:
a. Don’t bother worrying about it at compile-time. Use the INITIALIZE verb to initialize all data item occurrences in a table (at run-time) to their data-type-specific default values (numerics: 0, alphabetic and alphanumerics: SPACES).
b. Initialize small tables at compile time by including a VALUE clause on the group item that serves as a “parent” to the table, as follows:
05 SHIRT-SIZES VALUE “S 14M 15L 16XL17”. 10 SHIRT-SIZE-TBL OCCURS 4 TIMES. 15 SST-SIZE PIC X(2). 15 SST-NECK PIC 9(2).
c. Initialize tables of almost any size at compilation time by utilizing the REDEFINES clause: 05 SHIRT-SIZE-VALUES.
10 PIC X(4)
VALUE “S 14”.
10 PIC X(4)
VALUE “M 15”.
10 PIC X(4)
VALUE “L 16”.
10 PIC X(4)
VALUE “XL17”.
05 SHIRT-SIZES REDEFINES SHIRT-SIZE-VALUES. 10 SHIRT-SIZE-TBL OCCURS 4 TIMES. 15 SST-SIZE PIC X(2). 15 SST-NECK PIC 9(2).
Admittedly, the table shown in #28c is much more verbose than #28b. What is good about #28c, however, is that you can have as many FILLER/VALUE items as you need for a larger table (and those values can be as long as necessary!
Many COBOL compilers do not allow the use of VALUE and OCCURS on the same data item; additionally, they don’t allow a VALUE clause on a data item subordinate to an OCCURS. OpenCOBOL, however, has neither of these restrictions! Observe the following example, which illustrates the fourth manner in which tables may be initialized in OpenCOBOL:
05 X OCCURS 6 TIMES.
10 A PIC X(1) VALUE „?‟. 10 B PIC X (1) VALUE „%‟. 10 N PIC 9(2) VALUE 10.
In this example, all six “A” items will be initialized to “?”, all six “B” items will be initialized to “%” and all six “N” items will be initialized to 10. It’s not clear exactly how many times this sort of initialization will be useful, but it’s there if you need it.