• The Four Hundred
  • Subscribe
  • Media Kit
  • Contributors
  • About Us
  • Contact
Menu
  • The Four Hundred
  • Subscribe
  • Media Kit
  • Contributors
  • About Us
  • Contact
  • More About Commands and Variable-Length Parameters

    December 6, 2006 Ted Holt

    The code associated with this article is available for download.

    Last week, I told you about an easy way to power programming–creating CL commands with variable-length parameters. Using variable-length parameters lets you pass variables of different sizes to commands, instead of requiring that you use variables of certain lengths. It also helps you to solve certain problems once, and be done with them. This week, I am going to show you how you can make the variable-length parameter technique even easier.

    Last week’s command, ZEROSUP, invoked a CL program in order to strip leading zeros from a number stored in a character string. Instead of showing a user a confusing message, such as “00000080880 orders were loaded into the database,” you can send a clearer message, such as “80880 orders were loaded into the database.”

    dcl   &CustOrders      *dec       11 
    dcl   &AlphaNum        *char      12 
    
    chgvar    &AlphaNum    &CustOrders 
    zerosup   value(&AlphaNum) tovar(&AlphaNum) zerobal(*yes) 
    sndmsg    msg(&AlphaNum *bcat 'orders were added to the database.') + 
              tousr(Somebody)
    

    I wrote the command-processing program (CPP) for one reason–everybody has CL. However, the CPP does not have to be written in CL, and that leads me to this week’s tip: Consider using RPG for command-processing programs when variable-length parameters are involved.

    The reason is simple: RPG directly supports variable-length character data. All that’s required is to be able to spell the word varying.

    Let’s create another command to illustrate RPG’s suitability to the task at hand. This command will divide a character string into two strings by searching for a separator character. I’ll call it SPLITSTR (Split String). Here’s the source code:

    CMD        PROMPT('Split a string')                       
    PARM       KWD(STRING) TYPE(*CHAR) LEN(4096) MIN(1) +     
                 EXPR(*YES) VARY(*YES *INT2) +                
                 PROMPT('String to split')                    
    PARM       KWD(TOVAR1) TYPE(*CHAR) LEN(1) RTNVAL(*YES) +  
                 MIN(1) VARY(*YES *INT2) +                    
                 PROMPT('First receiving variable')           
    PARM       KWD(TOVAR2) TYPE(*CHAR) LEN(1) RTNVAL(*YES) +  
                 MIN(1) VARY(*YES *INT2) +                    
                 PROMPT('Second receiving variable')          
    PARM       KWD(DELIMITER) TYPE(*CHAR) LEN(1) +            
                 DFT(*BLANK) SPCVAL((*BLANK ' ')) +           
                 EXPR(*YES) PROMPT('Delimiting character')
    

    Notice that the first three parameters are all variable-length. The first parm, the string that is to be divided, is defined with a length of 4096. This means that the string to be divided can have a maximum of 4096 characters. The second and third parms, which contain the two resultant strings, are defined with a length of one. This means that the variables must be at least one byte long. They can be longer.

    Now let’s see how the parameters are defined to RPG. Here’s the procedure interface (the *ENTRY PLIST, but defined in the D specs).

    D SplitStr1       pi                         
    D  inFromString               4096a   varying
    D  ouToString1                4096a   varying
    D  ouToString2                4096a   varying
    D  inDelimiter                   1a          
    

    In the RPG program, I’ve defined all three parameters with their maximum lengths. The prefix on each parameter, which I can access through the %LEN built-in function, will give me their true lengths. This assignment statement tells me how long the input string was:

    Length = %len(inFromString);
    

    And these commands change the output parms without the undesired side-effect of changing other variables in memory.

    %subst(ouToString1:1:%len(ouToString1)) = ToString1;
    %subst(ouToString2:1:%len(ouToString2)) = ToString2;
    

    That is, if ouToString1 is 20 bytes long, the assignment only changes 20 bytes.

    Here’s an example of how you might use the SPLITSTR command:

    dcl &file *char 10                                                  
    dcl &lib  *char 10                                                  
                                                                        
    dcl &qualfile *char 21                                              
                                                                        
    splitstr  string(&QualFile) +
                 tovar1(&Lib) tovar2(&File) +
                 delimiter(/)
    

    Here a 21-byte variable contains a qualified file name. SPLITSTR divides the qualified name into library and file names by looking for a slash. If &QUALFILE has the value MYLIB/MYFILE, then &LIB is MYLIB and &FILE is MYFILE.

    Here’s a second example.

    dcl &AmtPosted *dec     (9 2)                                    
    dcl &AmtChar   *char     12                                      
                                                                     
    dcl &Dollars   *char      9                                      
    dcl &Cents     *char      2                                      
                                                                     
    chgvar    &AmtChar   &AmtPosted                                  
    ZeroSup   &AmtChar   &AmtChar                                    
    SplitStr  &AmtChar +
       tovar1(&Dollars) tovar2(&Cents) delimiter('.')
    

    Suppose that &AMTPOSTED has the value 395.81. CHGVAR loads &AMTCHAR with the value 0000385.81. The ZEROSUP command changes &AMTCHAR to 385.81 SPLITSTR loads 385 into &DOLLARS and 81 into &CENTS. Think about how you would accomplish the same task without the ZEROSUP and SPLITSTR commands. It’s not pretty, is it?

    I hope these articles have encouraged you to dig deeper into this greatly underused feature of OS/400 and i5/OS. To those iSeries and System i developers who have never written a command, I’ll pass along some advice my dad would give me as I faced new challenges while growing up, “You aren’t going to learn any younger.”

    RELATED STORIES

    Powerful Stuff: Creating Commands with Variable-Length Parameters!

    Variable-Length Character Data

    Share this:

    • Reddit
    • Facebook
    • LinkedIn
    • Twitter
    • Email

    Tags:

    Sponsored by
    WorksRight Software

    Do you need area code information?
    Do you need ZIP Code information?
    Do you need ZIP+4 information?
    Do you need city name information?
    Do you need county information?
    Do you need a nearest dealer locator system?

    We can HELP! We have affordable AS/400 software and data to do all of the above. Whether you need a simple city name retrieval system or a sophisticated CASS postal coding system, we have it for you!

    The ZIP/CITY system is based on 5-digit ZIP Codes. You can retrieve city names, state names, county names, area codes, time zones, latitude, longitude, and more just by knowing the ZIP Code. We supply information on all the latest area code changes. A nearest dealer locator function is also included. ZIP/CITY includes software, data, monthly updates, and unlimited support. The cost is $495 per year.

    PER/ZIP4 is a sophisticated CASS certified postal coding system for assigning ZIP Codes, ZIP+4, carrier route, and delivery point codes. PER/ZIP4 also provides county names and FIPS codes. PER/ZIP4 can be used interactively, in batch, and with callable programs. PER/ZIP4 includes software, data, monthly updates, and unlimited support. The cost is $3,900 for the first year, and $1,950 for renewal.

    Just call us and we’ll arrange for 30 days FREE use of either ZIP/CITY or PER/ZIP4.

    WorksRight Software, Inc.
    Phone: 601-856-8337
    Fax: 601-856-9432
    Email: software@worksright.com
    Website: www.worksright.com

    Share this:

    • Reddit
    • Facebook
    • LinkedIn
    • Twitter
    • Email

    Sponsored Links

    COMMON:  Join us at the Annual 2007 Conference & Expo, April 29 - May 3, in Anaheim, California
    Bug Busters Software Engineering:  Quality software solutions for the iSeries since 1988
    Profound Logic Software:  Experience RPGsp - the #1 iSeries Web development tool

    BOS Reduces Its Losses in the Third Quarter, Affirms 2006 Guidance The Business Case for the System iWant

    Leave a Reply Cancel reply

Volume 6, Number 43 -- December 6, 2006
THIS ISSUE SPONSORED BY:

IBS
WorksRight Software
Guild Companies

Table of Contents

  • Easily Calculating Statistical Functions
  • More About Commands and Variable-Length Parameters
  • Admin Alert: Quick and Dirty Ways to Find Job Gone Wild

Content archive

  • The Four Hundred
  • Four Hundred Stuff
  • Four Hundred Guru

Recent Posts

  • IBM Starts Winding Down Power10 System Sales
  • Guru: Service Programs And Activation Groups – Design Decisions That Matter
  • Strategic Topics To Think About For 2026, Part 1
  • Shield Gooses Performance Of Nagios Monitoring Tool, Adds AI Reporting
  • IBM i PTF Guide, Volume 28, Number 6
  • Rolling The Die In 2026: IBM i Predictions, Take Two
  • Perhaps 2026 Is The Year For Power Systems To Boom A Little
  • Guru: Binder Source Is Your Service Program’s Owner’s Manual
  • Skills Displaces Cybersecurity As Top Concern For IBM i Shops
  • IBM i PTF Guide, Volume 28, Number 5

Subscribe

To get news from IT Jungle sent to your inbox every week, subscribe to our newsletter.

Pages

  • About Us
  • Contact
  • Contributors
  • Four Hundred Monitor
  • IBM i PTF Guide
  • Media Kit
  • Subscribe

Search

Copyright © 2025 IT Jungle