Fixed-to-variable conversion in DFSORT means reading fixed-length (FB) input and writing variable-length (VB) output. Each output record has a 4-byte RDW (Record Descriptor Word) followed by the data, and the length of the data can vary from record to record. You might do this to trim trailing blanks, to output only selected fields so that record length depends on content, or to feed a downstream system that expects VB. This page covers how to produce VB output from FB input, the role of the RDW, using OUTFIL FTOV, and how to build shorter records when appropriate.
Fixed-length datasets use the same number of bytes for every record. If the real data is shorter, the rest is often padding (e.g. spaces). Variable-length format stores only the significant bytes (plus the RDW), so you can save space and avoid passing trailing blanks to programs that do not need them. Converting fixed to variable is also required when the target system or file format expects VB (e.g. some report files or interfaces).
When the output dataset is allocated with RECFM=VB, DFSORT writes each record as a 4-byte RDW followed by the data. You do not build the RDW in your control statements. You build only the data portion using OUTREC or OUTFIL BUILD. DFSORT (and the access method) compute the record length and write the RDW. So your BUILD specifies what data goes into the record; the length of that data can be the same for every record (effectively fixed-length data inside VB) or can vary if you build different lengths per record (e.g. by trimming or by including only certain fields).
To write variable-length output to the main sort output, allocate SORTOUT with RECFM=VB and LRECL set to the maximum record length (including the 4-byte RDW). For example, if the longest data record you will build is 200 bytes, use LRECL=204 (or a larger block-friendly value). In your JCL:
12//SORTOUT DD DSN=MY.VB.OUTPUT,DISP=(NEW,CATLG), // SPACE=(CYL,(5,2)),DCB=(RECFM=VB,LRECL=260,BLKSIZE=32760)
Your SORT or MERGE control statements and OUTREC (or INREC) build the data portion. DFSORT will write each record with the RDW and that data to SORTOUT.
When you have multiple output files (OUTFIL), one or more of them may need to be variable-length while the main SORTOUT might be fixed. The FTOV (fixed to variable) option on OUTFIL requests that that particular output file be written in variable-length format. The OUTFIL DD must be allocated with RECFM=VB and LRECL. Syntax is product-dependent; it is often specified as OUTFIL FILES=01,FTOV,... or OUTFIL OUTFIL FTOV,.... The record passed to that OUTFIL (after any BUILD) is written with an RDW so the file is VB.
If your input is fixed 80 bytes but you only need the first 40 bytes (or 40 bytes of significant data), build only those 40 bytes in OUTREC. Then the “data” portion of each VB record is 40 bytes; the RDW will reflect 44 (4 + 40). So you get variable-length output where each record is shorter than the input. Some products support “squeeze” or “trim” options that remove trailing spaces so that the data length varies by record (e.g. 35 bytes for one record, 40 for another). Check your DFSORT manual for BUILD options that allow variable-length build output.
| Term | Meaning |
|---|---|
| FTOV | Fixed to variable: output is RECFM=VB; each record has RDW + data. |
| VTOF | Variable to fixed: output is RECFM=FB; variable-length input is padded or truncated to fixed length. |
| RDW | Record Descriptor Word: 4-byte prefix on each VB record containing the total record length. |
| LRECL (VB) | Maximum record length including the 4-byte RDW; data can be shorter. |
Input is RECFM=FB, LRECL=80. You want VB output with only positions 1–20 and 41–60 (two 20-byte fields). Build a 40-byte data record; output will be 4-byte RDW + 40 bytes.
12OPTION COPY OUTREC BUILD=(1,20,41,20)
Explanation: BUILD=(1,20,41,20) takes bytes 1–20 from the input and places them at positions 1–20 of the build output, then bytes 41–60 (41,20 = start 41, length 20). The built record is 40 bytes. Allocate SORTOUT with RECFM=VB, LRECL=44 (or larger). DFSORT writes RDW + 40 bytes per record.
For RECFM=VB, LRECL is the maximum record length, and that maximum includes the 4-byte RDW. So if the longest data portion you build is 252 bytes, set LRECL to at least 256. Records shorter than that are valid; the RDW for each record will contain the actual length (4 + data length). Choosing an LRECL that is too small can cause truncation or errors; choosing one that is too large is safe but may affect blocking.
This page focuses on fixed input to variable output. If your input is already variable-length (VB), you can still produce variable-length output (e.g. after reformatting). The “fixed to variable” name refers to the input being fixed and the output being variable. For variable input to fixed output, see VTOF and variable-length records; for variable to variable you typically keep VB and may use OUTREC/OUTFIL to reformat the data portion.
Imagine every row in a notebook is exactly 10 boxes. That’s fixed length. Now we want to copy only the boxes that have something in them into another notebook where each row can be as short or long as we want. We look at each row, take the boxes we need (or the boxes that aren’t empty), and write them in the new notebook with a little label at the start that says how many boxes are in that row. That label is like the RDW. DFSORT does that: it takes fixed-length rows, builds the part we want (maybe shorter), and writes each row with a length label so the new file has variable-length rows.
1. What is fixed-to-variable conversion in DFSORT?
2. Who adds the RDW when writing variable-length output?
3. What is OUTFIL FTOV used for?
4. How can you make variable-length records shorter than the input fixed length?
5. For FTOV output, what must the output DD (SORTOUT or OUTFIL) have?