MainframeMaster
MainframeMaster

COBOL Tutorial

Progress0 of 0 lessons

COBOL Modular Programming

Modular programming is a software design approach that breaks large, complex programs into smaller, independent, reusable modules. In COBOL, modules are typically implemented as subprograms that can be called from main programs or other subprograms. Understanding modular programming principles is essential for creating maintainable, testable, and reusable COBOL applications that can scale and evolve over time.

What is Modular Programming?

Modular programming organizes code into logical, independent units called modules. Each module:

  • Has a Single Responsibility: Each module performs one specific function or handles one aspect of the application
  • Is Independent: Modules can be developed, tested, and maintained separately
  • Is Reusable: Well-designed modules can be used in multiple programs
  • Has Clear Interfaces: Modules communicate through well-defined parameters
  • Is Replaceable: Modules can be updated or replaced without affecting other parts of the system

In COBOL, modules are typically implemented as separate subprograms that are called using the CALL statement. This allows you to build complex applications from smaller, manageable pieces.

Benefits of Modular Programming

Modular programming provides numerous advantages for COBOL development:

Code Reusability

Write code once and use it in multiple places:

  • Common Functions: Create modules for common operations (date validation, calculations, formatting) that can be used across multiple programs
  • Consistency: Using the same module ensures consistent behavior across all programs that use it
  • Reduced Duplication: Avoid copying and pasting code, which leads to maintenance problems
  • Standardization: Establish standard ways of performing common tasks

Easier Maintenance

Fix bugs and make improvements in one place:

  • Single Point of Change: When you need to fix a bug or add a feature, you only need to modify one module
  • Reduced Risk: Changes are isolated to specific modules, reducing the risk of breaking other parts of the system
  • Easier Updates: Update a module once, and all programs using it benefit from the update
  • Version Control: Track changes to individual modules independently

Better Testing

Test modules independently:

  • Unit Testing: Test each module in isolation with controlled inputs
  • Isolated Testing: Test modules without needing the entire application
  • Easier Debugging: Problems are easier to locate when they're isolated to specific modules
  • Regression Testing: Test individual modules when making changes

Improved Readability

Smaller, focused modules are easier to understand:

  • Focused Purpose: Each module has a clear, single purpose that's easy to understand
  • Reduced Complexity: Smaller modules are less complex than large monolithic programs
  • Better Documentation: Modules can be documented individually with clear purposes
  • Easier Onboarding: New developers can understand modules one at a time

Parallel Development

Multiple developers can work simultaneously:

  • Independent Work: Different developers can work on different modules without conflicts
  • Faster Development: Work can proceed in parallel rather than sequentially
  • Specialization: Developers can specialize in specific types of modules
  • Reduced Dependencies: Well-designed modules have minimal dependencies on other modules

Modular Programming Concepts

Main Programs vs. Subprograms

In COBOL modular programming, there are two types of programs:

  • Main Program: The entry point of the application. It can call subprograms but is typically not called by other programs. Uses STOP RUN to terminate.
  • Subprogram: A program that is called by another program (main or another subprogram) to perform a specific function. Uses GOBACK to return control to the caller.
cobol
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
*> Main Program IDENTIFICATION DIVISION. PROGRAM-ID. MAIN-PROGRAM. PROCEDURE DIVISION. MAIN-LOGIC. DISPLAY 'Starting main program' CALL 'VALIDATE-DATA' USING INPUT-RECORD STATUS-CODE CALL 'PROCESS-DATA' USING INPUT-RECORD OUTPUT-RECORD CALL 'GENERATE-REPORT' USING OUTPUT-RECORD DISPLAY 'Main program complete' STOP RUN. *> Subprogram IDENTIFICATION DIVISION. PROGRAM-ID. VALIDATE-DATA. DATA DIVISION. LINKAGE SECTION. 01 LS-INPUT-RECORD PIC X(100). 01 LS-STATUS-CODE PIC 9(2). PROCEDURE DIVISION USING LS-INPUT-RECORD LS-STATUS-CODE. VALIDATE-PROCESSING. *> Validation logic here MOVE 0 TO LS-STATUS-CODE GOBACK.

The LINKAGE SECTION

Subprograms use the LINKAGE SECTION to define parameters received from calling programs:

  • No Storage Allocation: Unlike WORKING-STORAGE, the LINKAGE SECTION doesn't allocate storage. It references storage in the calling program.
  • Parameter Definition: Data items in the LINKAGE SECTION correspond to parameters passed in the CALL statement.
  • Efficient Passing: Parameters are passed by reference, meaning the subprogram accesses the same storage as the caller.
  • Two-Way Communication: Since parameters share storage, the subprogram can modify values that the caller can see.
cobol
1
2
3
4
5
6
7
8
9
10
11
12
13
IDENTIFICATION DIVISION. PROGRAM-ID. CALCULATE-TOTAL. DATA DIVISION. LINKAGE SECTION. 01 LS-QUANTITY PIC 9(5). 01 LS-UNIT-PRICE PIC 9(5)V99. 01 LS-TOTAL PIC 9(7)V99. PROCEDURE DIVISION USING LS-QUANTITY LS-UNIT-PRICE LS-TOTAL. CALCULATION-LOGIC. COMPUTE LS-TOTAL = LS-QUANTITY * LS-UNIT-PRICE GOBACK.

Parameter Passing

Parameters are passed using the CALL statement with the USING clause:

cobol
1
2
3
4
5
6
7
8
9
10
WORKING-STORAGE SECTION. 01 QUANTITY PIC 9(5) VALUE 100. 01 UNIT-PRICE PIC 9(5)V99 VALUE 25.50. 01 TOTAL-AMOUNT PIC 9(7)V99. PROCEDURE DIVISION. MAIN-LOGIC. CALL 'CALCULATE-TOTAL' USING QUANTITY UNIT-PRICE TOTAL-AMOUNT DISPLAY 'Total: ' TOTAL-AMOUNT STOP RUN.

In this example:

  • QUANTITY is passed to the subprogram's LS-QUANTITY
  • UNIT-PRICE is passed to the subprogram's LS-UNIT-PRICE
  • TOTAL-AMOUNT is passed to the subprogram's LS-TOTAL, which the subprogram calculates and returns

Designing Modular Programs

Single Responsibility Principle

Each module should have one clear purpose:

  • Focused Function: A module should do one thing well. For example, a date validation module should only validate dates, not also format them or perform calculations.
  • Clear Purpose: The module's purpose should be obvious from its name and documentation.
  • Avoid Mixing Concerns: Don't mix different types of operations (e.g., don't combine file I/O with calculations).
  • Easy to Describe: You should be able to describe what a module does in one sentence.

Module Organization Example

cobol
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
*> Main program coordinates modules IDENTIFICATION DIVISION. PROGRAM-ID. CUSTOMER-MANAGEMENT. PROCEDURE DIVISION. MAIN-CONTROL. *> Initialize system CALL 'INITIALIZE-SYSTEM' USING SYSTEM-STATUS *> Process customer data PERFORM UNTIL END-OF-FILE READ CUSTOMER-FILE CALL 'VALIDATE-CUSTOMER' USING CUSTOMER-RECORD VALIDATION-STATUS IF VALIDATION-OK CALL 'PROCESS-CUSTOMER' USING CUSTOMER-RECORD CALL 'UPDATE-CUSTOMER-FILE' USING CUSTOMER-RECORD END-IF END-PERFORM *> Generate reports CALL 'GENERATE-CUSTOMER-REPORT' USING REPORT-PARAMETERS *> Cleanup CALL 'CLOSE-FILES' USING FILE-STATUS STOP RUN.

This example shows a main program that coordinates several specialized modules:

  • INITIALIZE-SYSTEM: Handles system initialization
  • VALIDATE-CUSTOMER: Validates customer data
  • PROCESS-CUSTOMER: Performs business logic on customer data
  • UPDATE-CUSTOMER-FILE: Handles file updates
  • GENERATE-CUSTOMER-REPORT: Creates reports
  • CLOSE-FILES: Handles cleanup

Common Module Types

Typical modules in COBOL applications include:

  • Validation Modules: Validate data formats, ranges, business rules
  • Calculation Modules: Perform specific calculations (tax, interest, totals)
  • File Operation Modules: Handle file I/O operations
  • Formatting Modules: Format data for display or output
  • Report Generation Modules: Generate specific types of reports
  • Error Handling Modules: Handle errors and exceptions
  • Utility Modules: Provide common utility functions (date conversion, string manipulation)

Best Practices for Modular Programming

Follow these best practices for effective modular programming:

  • Keep Modules Focused: Each module should have a single, clear responsibility. If a module does multiple things, consider splitting it.
  • Use Descriptive Names: Module names should clearly indicate their purpose. For example, "VALIDATE-DATE" is better than "VD01".
  • Minimize Dependencies: Modules should have minimal dependencies on other modules. Avoid circular dependencies where module A calls module B, which calls module A.
  • Define Clear Interfaces: Use well-defined parameter lists. Document what each parameter is for, whether it's input, output, or both.
  • Handle Errors Appropriately: Modules should handle errors and return status codes or error indicators to the caller. Don't let errors propagate unexpectedly.
  • Document Modules: Document what each module does, its parameters, return values, and any side effects. This helps other developers understand and use the module.
  • Test Modules Independently: Test each module in isolation before integrating it into larger systems. This makes debugging easier.
  • Avoid Global State: Minimize use of global variables. Pass data through parameters instead. This makes modules more predictable and testable.
  • Version Modules: When updating modules, consider versioning to maintain compatibility with existing callers.
  • Reuse Existing Modules: Before creating a new module, check if an existing module already provides the functionality you need.

Example: Modular Customer Processing System

Here's a complete example showing how modules work together:

cobol
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
*> ============================================ *> Main Program: Customer Processing System *> ============================================ IDENTIFICATION DIVISION. PROGRAM-ID. CUSTOMER-PROCESSOR. DATA DIVISION. WORKING-STORAGE SECTION. 01 CUSTOMER-RECORD PIC X(200). 01 VALIDATION-STATUS PIC X. 88 VALID-RECORD VALUE 'Y'. 88 INVALID-RECORD VALUE 'N'. 01 PROCESSING-STATUS PIC 9(2). 01 FILE-STATUS PIC X(2). PROCEDURE DIVISION. MAIN-PROCESSING. *> Step 1: Initialize CALL 'INIT-FILES' USING FILE-STATUS IF FILE-STATUS NOT = '00' DISPLAY 'File initialization failed' STOP RUN END-IF *> Step 2: Process records PERFORM UNTIL END-OF-FILE READ CUSTOMER-FILE INTO CUSTOMER-RECORD AT END SET END-OF-FILE TO TRUE NOT AT END *> Validate CALL 'VALIDATE-CUSTOMER' USING CUSTOMER-RECORD VALIDATION-STATUS IF VALID-RECORD *> Process CALL 'PROCESS-CUSTOMER' USING CUSTOMER-RECORD PROCESSING-STATUS IF PROCESSING-STATUS = 0 *> Update CALL 'UPDATE-CUSTOMER' USING CUSTOMER-RECORD ELSE CALL 'LOG-ERROR' USING CUSTOMER-RECORD PROCESSING-STATUS END-IF ELSE CALL 'LOG-VALIDATION-ERROR' USING CUSTOMER-RECORD END-IF END-READ END-PERFORM *> Step 3: Finalize CALL 'CLOSE-FILES' USING FILE-STATUS CALL 'GENERATE-SUMMARY' USING SUMMARY-DATA STOP RUN. *> ============================================ *> Subprogram: Validate Customer *> ============================================ IDENTIFICATION DIVISION. PROGRAM-ID. VALIDATE-CUSTOMER. DATA DIVISION. LINKAGE SECTION. 01 LS-CUSTOMER-RECORD PIC X(200). 01 LS-VALIDATION-STATUS PIC X. PROCEDURE DIVISION USING LS-CUSTOMER-RECORD LS-VALIDATION-STATUS. VALIDATION-LOGIC. *> Perform validation checks *> (Simplified for example) MOVE 'Y' TO LS-VALIDATION-STATUS GOBACK. *> ============================================ *> Subprogram: Process Customer *> ============================================ IDENTIFICATION DIVISION. PROGRAM-ID. PROCESS-CUSTOMER. DATA DIVISION. LINKAGE SECTION. 01 LS-CUSTOMER-RECORD PIC X(200). 01 LS-PROCESSING-STATUS PIC 9(2). PROCEDURE DIVISION USING LS-CUSTOMER-RECORD LS-PROCESSING-STATUS. PROCESSING-LOGIC. *> Perform business logic *> (Simplified for example) MOVE 0 TO LS-PROCESSING-STATUS GOBACK.

This example demonstrates:

  • Main Program Coordination: The main program coordinates multiple specialized modules
  • Clear Separation: Each module handles a specific aspect (validation, processing, file operations)
  • Error Handling: Status codes are passed between modules to indicate success or failure
  • Modular Design: Each module can be developed, tested, and maintained independently

Explain Like I'm 5: Modular Programming

Think of modular programming like building with LEGO blocks:

  • LEGO Blocks are like modules—each block has a specific shape and purpose. You can use the same block (module) in many different buildings (programs).
  • Building a House is like creating a main program. You use different blocks (modules) for different parts: windows, doors, walls. Each block does its job, and you put them together to make the whole house.
  • Reusing Blocks is like code reusability. If you need a window in another house, you use the same window block (module) instead of making a new one.
  • Fixing Blocks is like maintenance. If a window block (module) has a problem, you fix that one block, and all houses using that block get the fix.
  • Different Builders can work on different blocks at the same time, just like different programmers can work on different modules.

So modular programming is like building with LEGO blocks—you create small, reusable pieces (modules) and put them together to build bigger things (programs). Each piece has a job, and you can use the same pieces in many different projects!

Practice Exercises

Complete these exercises to reinforce your understanding of modular programming:

Exercise 1: Identify Module Responsibilities

Review a COBOL program and identify functions that could be extracted into separate modules. List what each module would do and what parameters it would need.

Exercise 2: Create a Validation Module

Create a subprogram that validates a date in MM/DD/YYYY format. The module should receive the date string and return a status code indicating whether the date is valid.

Exercise 3: Create a Calculation Module

Create a subprogram that calculates the total cost (quantity × unit price) and applies a discount percentage. The module should receive quantity, unit price, and discount percentage, and return the total cost.

Exercise 4: Design a Modular System

Design a modular system for processing orders. Identify the main program and at least five subprograms, specifying what each would do and how they would communicate.

Exercise 5: Refactor a Monolithic Program

Take a simple monolithic COBOL program and refactor it into a main program and two or three subprograms. Document the changes and explain the benefits of the modular design.

Test Your Knowledge

1. What is the main benefit of modular programming?

  • Faster program execution
  • Breaking programs into smaller, reusable, maintainable modules
  • Reducing memory usage
  • Simplifying compiler options

2. How do you call a subprogram in COBOL?

  • PERFORM subprogram-name
  • CALL subprogram-name USING parameters
  • EXECUTE subprogram-name
  • RUN subprogram-name

3. Where do subprograms define parameters received from calling programs?

  • WORKING-STORAGE SECTION
  • LINKAGE SECTION
  • FILE SECTION
  • LOCAL-STORAGE SECTION

4. What statement does a subprogram use to return control to the caller?

  • STOP RUN
  • GOBACK
  • EXIT PROGRAM
  • RETURN

5. What is the single responsibility principle?

  • Each program should have only one variable
  • Each module should have one clear purpose or responsibility
  • Each program should call only one subprogram
  • Each module should use only one data type

6. What is code reusability?

  • Using the same variable names in multiple programs
  • Writing code once and using it in multiple places
  • Copying code between programs
  • Using the same compiler for all programs

Related Concepts

Related Pages