CAPL Script

What is CAPL Script?

Learning Objectives

After completing this article, you will be able to:

  • Understand CAPL's role and value in automotive electronics development and testing
  • Identify the four core application scenarios of CAPL
  • Recognize the basic structure of CAPL programs and their event-driven characteristics
  • Have a clear learning roadmap for the entire tutorial series

Let's Start with a Real Scenario

Imagine you're an automotive electronics engineer developing a door controller ECU. This controller needs to:

  • Receive lock/unlock commands from the central control system
  • Control window up/down movement
  • Send door lock status feedback to the instrument cluster

Here's the challenge: your ECU is still in development, and the instrument cluster, central control system, and other ECUs aren't ready either. How do you test your code?

At this point, you need a tool to "pretend" other ECUs exist, send test commands, and check whether your ECU responds correctly.

This tool is CANoe, and the language that makes CANoe "listen to you" is CAPL, which we'll explore today.


What is CAPL?

CAPL (Communication Access Programming Language) is a specialized programming language developed by Vector for CANoe/CANalyzer software.

You can think of it as:

CAPL is the "scripting language" for CANoe, allowing you to programmatically control everything on the bus.

If you're familiar with C language, you'll find CAPL's syntax very similar. However, CAPL has two significant characteristics:

1. Event-Driven

Traditional C programs start executing sequentially from main(). CAPL programs, on the other hand, are passively responsive - they wait for events to occur, then react.

For example:

  • Receiving a CAN message → Triggers on message event
  • Pressing a key on the keyboard → Triggers on key event
  • Timer expiration → Triggers on timer event

2. Bus-Oriented

CAPL is inherently designed for automotive buses. It has built-in data types like message and signal, allowing direct reading and writing of CAN/LIN/FlexRay bus data.


What Can CAPL Do?

CAPL has four core application scenarios:

1. Simulation

Simulate an ECU that doesn't exist yet.

Returning to the opening example: You can use CAPL to write a "virtual central lock" that periodically sends lock/unlock commands, making your door controller believe a real central lock is working.

variables
{
    msTimer SendLockCommand;  // Timer declaration
}

on start
{
    setTimer(SendLockCommand, 1000);  // Start timer on measurement start
}

on timer SendLockCommand
{
    message CAN1.0x200 lockCmd;
    lockCmd.RTR = 0;
    lockCmd.DLC = 1;
    lockCmd.byte(0) = 0x01;  // Lock command
    output(lockCmd);
    setTimer(SendLockCommand, 1000);  // Repeat every 1 second
}

2. Test

Check a defined requirement using a new observation and a bounded wait.

A stored doorStatus == 1 may come from an earlier message. Sending a new command, waiting 500 ms and reading that variable can report success even if no new response arrived. A proper test must establish freshness, validate the triggering frame's channel, direction and DLC, and define how the response relates to the request.

Start with the narrower heartbeat availability test. It separates timeout, interruption, data retrieval and payload errors. Its passing result means a valid heartbeat was observed, not that a door locked. A real command test needs the ECU's actual protocol and correlation rules.

3. Diagnostics

Send and respond to diagnostic requests.

When you need to read ECU fault codes, flash software, or perform UDS (Unified Diagnostic Services), CAPL can help you construct and parse diagnostic messages.

4. Gateway/Analysis

Forward messages between different buses, or monitor and analyze data flow.

For example, forwarding messages from CAN1 (CAN bus 1) to CAN2 (CAN bus 2):

on message CAN1.*
{
    // Special syntax: create a message for CAN2 with same ID as received message
    message CAN2.* msg;
    if (this.dir != rx) return;  // Only process received messages
    msg = this;  // Copy received frame
    msg.CAN = 2;  // Select destination after copying
    output(msg);
}

Scope: This forwarding fragment is for an isolated classical CAN configuration. The wildcard object receives the ID through assignment; explicitly set the destination channel after copying. Do not add a reverse forwarding path without loop prevention.


What Does a CAPL Program Look Like?

Let's look at the simplest CAPL program:

on key 'a'
{
    write("Hello CAPL!");
}

What does this code do?

  1. on key 'a' — When the user presses the a key on the keyboard
  2. write("Hello CAPL!") — Outputs a line of text in CANoe's Write window

That's it! No main() function, no complex initialization. When an event occurs, the code executes.

Let's look at a slightly more complex example - responding to CAN messages:

// Note: EngineData message and EngineSpeed signal must be defined in DBC database
on message EngineData
{
    if (this.EngineSpeed > 3000)
    {
        write("Warning: Engine speed is high!");
    }
}

This code checks the EngineSpeed signal within the EngineData CAN message when received. If the engine speed exceeds 3000, it outputs a warning.

Tip: this.EngineSpeed this direct signal access method requires EngineData message and EngineSpeed signal to be defined in the DBC database first.


Learning Roadmap for This Tutorial

This series consists of 8 articles that will take you from zero to mastering CAPL:

Article Topic What You'll Learn
Article 1 What is CAPL? Understanding and positioning (this article)
Article 2 Development Environment Setup Create and run your first CAPL program
Article 3 Programming Basics Variables, functions, CAPL-specific types
Article 4 Core Interactions Event-driven model, database integration
Article 5 Debugging Techniques Breakpoints, logs, error troubleshooting
Article 6 Simulation Node Development Build a complete virtual ECU
Article 7 Test Module Development Write automated test cases
Article 8 Comprehensive Project Complete closed loop of simulation and testing

Articles 6 and 8 share the door model. Article 7 uses a separate heartbeat contract to teach bounded waits; its method can be adapted only after changing the expected protocol.


Article Summary

Through this article, we've learned:

  • CAPL is a specialized programming language for CANoe/CANalyzer, used for simulation, testing, diagnostics, and analysis
  • CAPL is event-driven: programs respond to events (message arrival, key presses, timers) and execute
  • CAPL is bus-oriented: it has built-in data types like message and signal
  • CAPL syntax is similar to C language; engineers with programming background can quickly get started

Exercises

  1. Reflection Question: In your current work, what scenarios could CAPL solve? (Hint: Consider simulation, testing, and diagnostics)

  2. Preview Task: If you already have CANoe installed, try opening a sample project and look for .can files (these are CAPL source code) to browse their structure.