To determine the length of data (i.e., text) in a CL variable, you can use the legacy looping methodology, or something that's been available for a long, long time.
The RTVMSG CL command is used to retrieve the first or second-level text of a message. While retrieving the message text, the programmer may specify the message's message data.
The RTVMSG command inserts the message data passed by the programmer into the substitution variables embedded in the original message.
Originally, IBM provided CPF9898 to send ad hoc program messages with user supplied message text. The problem was that most programmers also embedded a period at the end of their ad hoc messages, and CPF9898 includes a period as well. So "Hello World." was sent as "Hello World.." and "Hello World!" showed up as "Hello World!." which was often not what was expected.
To solve this every IT shop could create their own message file and then add a so called "blank" message. However, during the lifecycle of AS/400 they included the new CPF9897 message, which is a blank, blank message.
CPF9897 contains 1 substitution variable and nothing else. So sending a message using CPF9897 produces a message with exactly what you type in.
In addition to sending messages, you can also use CPF9897 on the RTVMSG command. RTVMSG will return the first-level (or 2nd-level) message text for a given message ID. The program may specify the so called "message data" and the system embeds that data into the message before returning it.
Since CPF9897 contains just '&1' and nothing else, it return whatever the message data contains during the send or retrieve operations.
The RTVMSG command will also return the length of the message text returned. It does this on the MSGLEN parameter. The programmer passes a CL variable with the definition of TYPE(*DEC) Len(5 0) and the length of the message is returned.
Putting this all together, we realize that that RTVMSG command can also be used to retrieve the length of the data in a CL variable, if using CPF9897 or a similar user-created message ID.
PGM /* Find length of the data in a field */ DCL VAR(&NAME) TYPE(*CHAR) LEN(20) + VALUE('Bob Cozzi') DCL VAR(&LEN) TYPE(*DEC) LEN(5 0) /* Use RTVMSG with CPF9897 to get the length */ RTVMSG MSGID(CPF9897) MSGF(QCPFMSG) + MSGDTA(&NAME) MSGLEN(&LEN) /* The field &LEN contains the length of the */ /* text in the &NAME variable. */ ENDPGM