flocate() — Locate a VSAM record
Standards
Standards / Extensions | C or C++ | Dependencies |
---|---|---|
Language Environment | both |
Format
#include <stdio.h>
int flocate(FILE *stream, const void *key, size_t key_len, int options);
#define _OPEN_SYS_UNLOCKED_EXT 1
#include <stdio.h>
int flocate_unlocked(FILE *stream, const void *key, size_t key_len, int options);
General description
Moves the VSAM file position indicator associated with the stream pointed to by stream, according to the rest of the arguments specified.
To avoid infringing on the user's name space, this nonstandard function has two names. One name is prefixed with two underscore characters, and one name is not. The name without the prefix underscore characters is exposed only when you use LANGLVL(EXTENDED).
To use this function, you must either invoke the function using its external entry point name (that is, the name that begins with two underscore characters), or compile with LANGLVL(EXTENDED). When you use LANGLVL(EXTENDED) any relevant information in the header is also exposed.
key points to a key used for positioning.
- KSDS, KSDS PATH, and ESDS PATH
- The key can point to a field of any storage type except register. Typically it points to a character string whose length is key_len. The key_len must be less than or equal to the key length of the data set. If key_len is the same as the file's key length, a full key search is automatically used; otherwise, a generic search is used. A generic key search is one in which the search key is a leading portion of the key field. The record positioned to is the first of the records having the same generic key.
- ESDS
- The key points to a relative byte address that may be stored as 4 or 8 byte value. key_len is either 4 or 8.
- RRDS
- The key points to a relative record number stored as an unsigned long int. key_len is either 4 or 8.
options specifies the position options described in Table 1.
__KEY_FIRST | Positions to the first record in the file. Subsequent reads are in the forward direction. key and key_len are ignored. |
---|---|
__KEY_LAST | Positions to the last record in the file. Subsequent reads
are in backward order. key and key_len are
ignored. Only applies to VSAM files opened in record mode. |
__KEY_EQ | Positions to the first record with the specified key. Subsequent reads are in the forward direction. |
__KEY_EQ_BWD | Positions to the first record with the specified key. Subsequent
reads are in backward order. Using this option requires a full key
search. Key_len must be equal to the key length as defined for the
data set. Only applies to VSAM files opened in record mode. |
__KEY_GE | Positions to the first record with a key greater than or equal to the specified key. |
__RBA_EQ | Positions to the record with the specified RBA. Subsequent
reads are in the forward direction. You cannot use __RBA_EQ with an alternative index path. Using this option with RRDS is not recommended. The underlying VSAM utilities do not support seeking to an RBA in an RRDS file. The flocate() function attempts to convert the RBA to a Relative Record Number by dividing the value by the LRECL of the file and using the equivalent __KEY_EQ. Using this option with KSDS is not recommended because the RBA of a given record may change over time, because of inserts, deletions, or updates of other records. |
__RBA_EQ_BWD | Positions to the record with the specified RBA. Subsequent
reads are in backward order. You cannot use __RBA_EQ_BWD with an alternative index path. Using this option with RRDS is not recommended. The underlying VSAM utilities do not support seeking to an RBA in an RRDS file. The flocate() function attempts to convert the RBA to a Relative Record Number by dividing the value by the LRECL of the file and using the equivalent __KEY_EQ_BWD. Using this option with KSDS is not recommended because the RBA of a given record may change over time, because of inserts, deletions, or updates of other records. Only applies to VSAM files opened in record mode. |
_KEY_EQ_BWD | Positions to the first record with the specified
key. Subsequent reads are in backward order. Using this option requires a full key search. key_len must be set equal to the key length as defined for the data set. Only applies to VSAM files opened in record mode. |
- When you are trying to use flocate() in a path to a nonunique key, the resulting position will be at the first physical record of the duplicate key set.
- flocate() releases all record locking.
- Writes to VSAM data sets are not affected by preceding calls to flocate().
- If a record was not found, you must successfully relocate to another position before reading or writing (using the flocate() function). The exception to this is that a write that follows a failed flocate() will succeed if the file was opened for initial loading, but no records have been written to it yet.
flocate_unlocked() is functionally equivalent to flocate() with the exception that it is not thread-safe. This function can safely be used in a multithreaded application if and only if it is called while the invoking thread owns the (FILE*) object, as is the case after a successful call to either the flockfile() or ftrylockfile() function.
Considerations for VSAM extended addressability data sets: flocate() accepts key lengths of 4 or 8 when relative byte address (RBA) values are used for positioning. A key length of 8 is required only when the working with a VSAM extended addressability data set, because when the address grows past the 4GB boundary, the key needs to be large enough to hold the value.
When using the value 4GB-1 as the key to flocate(), the key length must be 8 and the data type used must be 8 bytes in size (for example, X' 00000000FFFFFFFF') . If the key length is 4, flocate() treats the key as -1(EOF).
Returned value
If successful, flocate() returns 0.
If a record was not found or the position is beyond the EOF, flocate() returns EOF.
Example
#include <stdio.h>
int main(void)
{
FILE *stream;
int vsam_rc;
char *key = "RECORD 27";
stream = fopen("DD:MYCLUS", "rb+,type=record");
vsam_rc = flocate(stream, key, 9, __KEY_EQ);
⋮
}