Page tree
Skip to end of metadata
Go to start of metadata

Object dependency execution is done by coding from SAP_APPL. Therefore it’s not available in non-ERP
systems (exception: Low Level Configuration).

There are two types of object dependencies:
- Classic object dependencies: Preconditions, Selection conditions, Procedures, Actions
- Constraints (not executed in Classification and Low Level Configuration; can be assigned to Configuration Profiles only)

Classic object dependencies can be linked to a large number of objects. To do so, internal pointer KNOBJ is stored within
application table of objects (e.g. STPO-KNOBJ for BOM items).

 

What are the different object dependencies types used for?

  • Precondition:
    Determine whether an object (e.g. char or char value) should be displayed.
  • Selection Condition:
    Determine whether an object (e.g. BOM item) is valid and should be used. If assigned to a characteristic, the
    char is required, if SelCond is fulfilled
  • Action & Procedure:
    Are used to calculate values.
    (Actions are obsolete and should not be used anymore. Nevertheless they are still supported.)


KNOBJ is a reference to CUOB-KNOBJ to create a link to the internal object dependecy key KNNUM. KNNUM is assigned to
external name, status etc. by table CUKB.

In object dependencies it’s important where a value comes from, cause different authors are not allowed to overwrite existing values.
Different valuation by different authors will result in char valuation conflicts (inconsistencies). Field name normally is ATAUT or KNTYPE.
Database and ABAP-Runtime use different ‘codes’.

DatabaseRuntimeAuthor
SPACEDESet by User
 8SFDefault
Can be overwritten by any author; Default can be set in master data or in object dependency using function $SET_DEFAULT
 2ACAction
 3SCSelection condition
 4CLClassification
 5CSConstraint
 6DDDDB management

Intersection build for restrictable chars

 7PRProcedure


Classic object dependency execution is triggered by events, like the user pressing <enter> key. At one time only the object dependency linked
to a single object is executed. Sequence of  object dependencies and objects is well-defined.

When a configurable item is configured, sequence of object dependencies is as follows:

  1. Withdraw values set by Action or Procedure
  2. Actions are executed up to 25 times
    1. Actions assigned to configuration profile
    2. Actions assigned to characteristics
    3. Actions assigned to char values
  3. Procedures assigned to configuration profile
  4. Procedures assigned to characteristics
  5. Procedures assigned to char values
  6. Actions again are executed up to 25 times (profile, char and char value)
  7. Selection conditions assigned to the object (e.g. BOM item)
  8. Actions assigned to the object, if SelCond is fulfilled
  9. Procedures assigned to the object, if SelCond is fulfilled
  10. Preconditions assigned to characteristics
  11. Preconditions assigned to char values

 

When a non-configurable item is configured, sequence of  object dependecies is as follows:

  1. Selection conditions assigned to the object (e.g. BOM item)
  2. Actions assigned to the object, if SelCond is fulfilled
  3. Procedures assigned to the object, if SelCond is fulfilled

Classification data can be used instead of Selection conditions.

The sequence of actions assigned to a single object is undefined. Sequence of procedures can be defined by user (column
in assignment screen).

Remark: Constraints are executed whenever an ‘input’ characteristic is changed. Constraint execution is not linked to
events or instances.

Business Overview

The ERP variant configurator is used to create and check characteristic value assignments for configurable objects, to calculate
condition keys for value based surcharges and to perform value based structure determinations (BOM explosions). There are
different types of configurable objects like e.g. materials (KMAT), standard nets (projects), routings.

Fig 1: Typical scenario: Sales of configurable Material

The typical use case is the configuration of materials in scenario 'sales of configurable materials' in ERP-SD:

  • A sales person creates an SD order with an item holding a configurable material.
  • The interactive (high level) variant configurator is invoked and the user specifies the configuration of this item in terms of characteristic
    value assignments in the configurator UI.
  • The configuration is checked for completeness and consistency against the configuration model of the KMAT to ensure that the ordered
    item is buildable: this includes evaluation of dependencies to check validity of assigned values and to calculate additional (dependent) values.
  • The configurator can determine dynamic pricing condition keys (variant conditions) for feature based pricing.
  • If the configuration is consistent and complete and matches the customer's requirements the user returns to the sales order screen and
    saves the configuration along with the configurable item
  • The configuration data created in this interactive ('high level') configuration are later used for planning and manufacturing of the configured
    material. These subsequent steps involve non-interactive ('low level') configuration, e .g. for manufacturing BOM explosion and routings.

 

Dependencies

Types of Dependencies

Dependencies are used to check consistency of the configuration and to calculate dependent elements in the configuration. The variant configurator
supports different types of dependencies:

Type

Purpose

High Level Only

Declarative

Selection Condition

Define an element as 'mandatory' based on other input to the configuration.
Elements: BOM item, characteristic

No

No

Precondition

Define an element as 'forbidden' based on other input
Elements: characteristic, characteristic value

No

No

Procedure

Calculate dependent elements
Examples: characteristic value, default, variant condition key, variant condition factor
Procedures can be attached to config profiles (-> KMATs), characteristics and characteristic values.

No

No

Action

Similar to procedures (obsolete)

No

('kind of'' - see below)

Constraints

Check consistency of a combination of objects and
characteristic values, calculate dependent elements.
A constraint can refer to a combination of different instances in the configuration, e.g. to a KMAT and one or several parts.

Yes

Yes

'High Level Only' indicates that the type of dependencies can only be used in 'high level' configuration (KMAT).
'Declarative' indicates that dependencies bring their own implicit control logic: no sequence numbers or ordering by the calling application is required;
the result of applying the dependencies is independent of the sort order in which they are evaluated.
Dependencies marked in light grey are called 'classic dependencies'; these are all dependency types with the exception of constraints.
The evaluation of constraints differs significantly from the evaluation of 'classic dependencies' and is not covered in this document.
Actions are classified as 'kind of declarative' because they are evaluated up to 25 times in a loop: in this way output of an action can serve as input to
another action regardless of their detailed evaluation sequence. Running all actions 25 times is, of course, an arbitrary limitation and generally
not too efficient.

Object dependency execution is triggered by (SAPLCEI0)EVALUATE_DEPENDENCY_KNOWLEDGE.

High Level Configuration

While executing object dependencies characteristic valuation is stored in function group CUDB. (CUDB is often called DynamicDataBase, DDB).
Some important breakpoints:

Function ModuleDescription
CUDB_INITInitialize char valuation buffer
CUDB_SAVE_TMPBuffer current char valuation
CUDB_LOAD_TMPRestore current valuation from buffer
CUDB_SET_VALSet single char value
CUDB_DEL_VALDelete single value
CUDB_RESTRICT_DOMRestrict values of restrictable char

 

Important global variables are:

Function ModuleDescription
CUDBD_TO_FACT_IList of instances in multi-level configuration
CUDBD_AW_FACT_Iurrent values (non-restrictable chars) More than one value for the same char means either a multi-value char or a conflict
CUDBD_AZW_FACT_IRestrictable chars. Field F points to DOM_IDX
CUDBI_SYM_DOMSList of char values (ref by CUDBD_AZW_FACT_I)
CUDBI_NUM_DOMSList of num values (ref by CUDBD_AZW_FACT_I) (SAPLCUTM)
 CUTMD_JUSTIFICATION Author of values in CUDB (CUDBD_A(z)W_FACT_I -F -> CUTMD_JUSTIFICATION-FACT)

 

Execution of classic OD is done in function group CUOV:

Function ModuleDescription
CUOV_DO_PROCEDUREExecute procedure
CUOV_DO_ACTIONExecute action
CUOV_EVAL_PRECONDITIONSEvaluate precondition
CUOV_EVAL_SEL_CONDITIONSEvaluate selection condition

 

Important global variables are:

Global variableDescription
CUOVD_KNNUMKNNUM of current OD
CUOVD_SELFPointer to current SELF instance in CUDB
CUOVD_PARENTPointer to current PARENT instance in CUDB
CUOVD_ROOTPointer to current ROOT instance in CUDB

 

 

Low Level Configuration

Low Level Configuration is used for MRP, calculation, routing etc.

In Low Level an object dependency assigned to the configuration profile is not executed. In Low Level char values can be calculated
for $SELF instance only. Execution is done in function group CULL. (CUDB and CUOV are not used.)   CULL_INIT Initialize new
Low Level configuration and set configuration date.

CULL_MAKE_INSTANCE Define instance. ITYPE provides class type and object (material) PROPERTIES is a list of char values

CULL_CONFIGURE_ITEM Configure single item. First selection condition is evaluated. If the item has classification data, this can
be used as selection condition instead. If selection condition is fulfilled, procedures are executed. If values are calculate by
dependency, those inferred values are returned.

 

Variant functions

Variant functions are called from CUFC_FUNCTION_CALL in High- and Low-Level Configuration.

If call is done by PFUNCTION statement GLOBALS parameter is filled and access to CUPR functions is allowed to set characteristic
values. If call is done by FUNCTION statement GLOBALS parameter is not filled. Access to CUPR functions is not permitted.

In both cases results may be returned for characteristics defined in CU65, CU66, CU67 by table MATCH. Access to QUERY and MATCH
table is done by CUOV_GET_FUNCTION_ARGUMENT and CUOV_SET_FUNCTION_ARGUMENT.

Maintenance of Dependencies

VC dependencies are written in a special dependency syntax using the VC dependency editor (cu01-cu03). The syntax allows
the modeller to refer to other VC master data like characteristics, values, classes/materials.

Screenshot: Dependency Editor with a simple selection condition

For classic dependencies, the system stores the following data:

Table

Content

CUKB

Basic data (depdency type KNART, admin info etc)

CUKBT

Language dependent descriptions

CUKN

Source code

CUEX

Runtime code format

CUOB

Allocation of dependency to a 'carrier' object: the 'carrier' object can be a configuration profile, BOM item, characteristic, value etc.

CUXREF

Cross references (master data objects referenced in a dependency)

Details about VC dependency maintenance are described in a different handover document.

Generally, VC master data are maintained in separate transactions per object. As of ERP 5.0, the PME VC integrated modelling environment with an
improved dependency editor is available to create VC master data from a model view. Replication of VC master data between different ERP systems
is usually done via ALE (IDocs). A detailed overview of VC data is given in the corresponding VC training classes (LOVC990) and in the SAP Online
Help Portal.

The following tables is meant as a short overview and reminder:

Object

Transaction code

Main DB tables

Bill of Materials

cs01-03

MAST, STPO

Characteristic

ct04

CABN, CABNT, CAWN, CAWNT

Class

cl01-03, cl22n

KLAH, KSSK, KMSL

Configuration Profile

cu41-43

CUCO

Constraint Net

cu21-23

CURSVAR, CURSPAT, CURSSPN, CURSDNN, CURSCOD

Dependency

cu01-03

CUKB, CUKBT, CUKN, CUOB, CUEX

Material

mm01-03

MARA

UI Design (Cstic groups)

cu50

CECUSD, CECUSDT, CECUFM

Value specific pricing surcharge
('1:1 variant condition')

cu50

MACOND

Variant Function

cu65-67

CUVFUN

Variant Table

cu61-63, cu60

CUVTAB

Runtime Evaluation of Dependencies

Runtime evaluation of classic dependencies is based on interpretation of the runtime code format. For high level configuration interpretation
is done in function group CUOV - which is the topic of this document - and for low level configuration interpretation is done in function group CULL.

 

Architecture

 

 

 

  • The variant configurator accesses configuration master data of the configurable object to retrieve the following information:
    • Configuration profiles
    • Classes, characteristics and their values (domains, defaults, facets)
    • BOM structure
    • Dependencies attached to config.profile, characteristics, values, BOM items etc
    • Variant tables used in dependencies
  • A configuration consists of instances, characteristics and values
    • Instances correspond to items in the sales order
    • A 'single level' configuration contains exactly one (root) instance
    • A multi-level configuration contains a tree of instances
  • The configuration can hold additional transient data like e.g. dynamic domain restrictions (for F4 help) or information about visibility and
    availability for input of characteristics
  • The configuration is represented in a two-tiered fashion:
    • External layer (CEI0): this is used to communicate with the user interface and with external APIs
    • Internal layer (CUDB): this serves as the 'working memory' for dependency evaluation
    • Both layers are kept in sync via a pull mechanism: in this way, inferences and status information (conflicts) calculated from dependencies
      are made known to the external problem solver / User Interface.
  • The configuration is built-up from
    • Static model data (defaults, fixed BOM components)
    • User selections
    • Dynamic model inferences (values calculated from dependencies, BOM items with selection conditions)
  • The configuration is checked at certain points in time - e.g. after each user input:
    • As part of the check function, classical dependencies are evaluated and inferences and consistency status are re-calculated.

 

Design

Interpretation of classic dependencies in high level configuration is performed in function group CUOV. The interpreter is designed
in 'old style' (non-OO) ABAP using function modules and formroutines.

Function Modules

The main function modules in function group CUOV are the following:

Function Module

Description

Callers

CUOV_CHECK_CONDITION

Check a list of conditions
(pre- or selection conditions)

CLKNE_CONFIGURE_OBJECT,
CUD0_CONFIGURE_OBJECT

CUOV_DO_PROCEDURE

Evaluate a list of procedures

CLKNE_CONFIGURE_OBJECT,
CUD0_CONFIGURE_OBJECT

CUOV_DO_ACTION

Evaluate a list of actions

CLKNE_CONFIGURE_OBJECT,
CUD0_CONFIGURE_OBJECT

CUOV_SET_OVARS

Assign DDB instance numbers to instance variables $ROOT, $PARENT and $SELF

CE_I_CONFIGURE,
CUD0_CONFIGURE_OBJECT

Note: Functions CUOV_EVAL_* are similar to these function modules but are currently not used (no static reference found). They accept the dependency
identifiers (KNNUM) instead of the code tables as input.

The following auxiliary function modules exist for tracing dependency evaluation:

Function Module

Description

Callers

CUOV_TRC_INIT

Initialize trace

Invoked dynamically from SAPLCUTC

CUOV_TRC_DETAIL

Display trace detail

Depreceated

CUOV_ACT_TRC_DETAIL

Display trace details for actions

Invoked dynamically from SAPLCUTC

CUOV_PCND_TRC_DETAIL

Display trace details for preconditions

Invoked dynamically from SAPLCUTC

CUOV_SCND_TRC_DETAIL

Display trace details for selection conditions

Invoked dynamically from SAPLCUTC

CUOV_PROC_TRC_DETAIL

Display trace details for procedures

Invoked dynamically from SAPLCUTC

The following utility function modules exist:

Function Module

Description

Callers

CUOV_GET_CURRENT_DEPENDENCY

Return basic data (CUKB) of the currently processed dependency

 

CUOV_GET_FUNCTION_ARGUMENT
CUOV_SET_FUNCTION_ARGUMENT

Read or write actual parameters in a variant function interface

Customer specific code implementing variant functions

CUOV_GET_VARS

Extract variables from dependency code

Explanation (SAPLCUXP)

Data Structures

 

Classic dependency evaluation is based on two kinds of input data:

  • Dependency code to be interpreted
  • Working memory (Dynamic Database = DDB) against which dependencies are evaluated

CUOV dependency evaluation functions expect an an input parameter (table) with dependency code. In addition, CUOV has a global memory
with DDB instance numbers for instance variables $ROOT, $PARENT, $SELF to read or write data in the dynamic database during evaluation.
The DDB is managed in function group CUDB which provides access functions to read and write entries in the DDB.

Additional global memory variables in CUOV are the following (see include lcuovtop):

Data

Description

Comments

CUOVD_KNNUM

Internal ID of currently processed dependency

 

CUOVD_RETCODE

Error return code of dependency processing

 

CUOVD*_TRC*

Trace settings and trace content recorded in the current session

 

CUOVD*_MTRC*

New Trace settings and trace content recorded in the current session

New trace introduced with OSS note 800863

Note: all data in the global memory of CUOV are transient, i.e. they are not saved together with the configuration.
Only trace settings can be saved in the trace modules (CUTC).

 

Code Format of Classic Dependencies

The code format of classic dependencies is a binary tree consisting of one or several nodes: each node represents a term.

Example: code tree for condition <variable_1> EQ 'XYZ' OR <variable 2> EQ 'UVW

 

 

In ABAP, the tree is represented as an internal table of lines with structure KBD_TREE:

Component

Datatype

Comments

TYPE

CHAR4

Type of term

OP

CHAR32

Extended operator

ARG1

CHAR6 (storing an integer with sign)

Reference to a child term in KBD_TREE

ARG2

CHAR6 (storing an integer with sign)

Reference to a child term in KBD_TREE

Note: The reference to the child term is stored as a table line 'offset': if the current term is in table line idx, the left child term is found in table line
idx + arg1 and the right child term is found in table line idx + arg2. A tree node can be re-used as child term in different parent terms (code compression).
The sort order of KBD_TREE lines must not be changed !

Example: Code table KBD_TREE for selection condition ak_color = 'RAL4711' OR ak_fabric = '001'

The code tree can be viewed by selecting the detailed view of a dependency in transaction cu04 and by clicking the 'Compilation' button.

 

Explanation of code table entries:

Line No

TYPE

OP

ARG1

ARG2

Comment

000001

blog

OR

1

5

Binary logical operator term (OR)
First partial condition term is in line <line no> + arg1 = 1+ 1 = 2.
Second partial condition term is in line <line no> + arg2 = 6

000002

sxpr

EQ

1

3

Term representing the symbolic comparison expression
ak_color = 'RAL4711'

000003

avar

0000006028

1

0

Term representing variable $root.ak_color;
Characteristic ak_color is identified via its internal system number (ATINN) in the OP field

000004

sym

$ROOT

5

0

Symbol identifying the instance variable (one of $root, $parent, $self).
$root is the default instance variable which is used unless you explicitly specify $parent or $self in the dependency source code.

000005

qlit

RAL4711

7

0

Quoted literal (constant) representing the right hand side of the symbolic comparison expression
ak_color = 'RAL4711'
ARG1 contains the length of the literal.

000006

sxpr

EQ

1

2

Term representing the symbolic comparison expression
ak_fabric = '001'

000007

avar

0000006029

3-

0

Term representing variable $root.ak_fabric.
The negative value of ARG1 indicates that an existing term in line 7-3 = 4 is used for the instance variable ($root).

000008

qlit

001

3

0

Quoted literal (constant) representing the right hand side of the symbolic comparison expression
ak_fabric = '001'

In the appendix you can find more examples of code trees including also other syntax elements.

 

Term types, operators and arguments in classic dependencies:

Type
TYPE

Description

Operator
OP

Left Child
ARG1

Right Child
ARG2

Logical Terms

blog

Binary logical operator term

AND, OR

<condition 1>

<condition 2>

ulog

Unary logical operator term

NOT

empty (0)

<condition>

sxpr

Symbolic comparison expression

EQ, NE, GT, LT, GE, LE

<operand 1>

<operand 2>

nxpr

Numeric comparison expression

EQ, NE, GT, LT, GE, LE

<operand 1>

<operand 2>

oxpr

Object comparison expression

EQ, NE, GT, LT, GE, LE

<operand 1>

<operand 2>

Numeric Terms

bnum

Binary numeric operator term

+, -, *, /, **

<operand 1>

<operand 2>

unum

Unary numeric operator term

- (minus)

empty (0)

<operand>

fnum

Builtin numeric function term

See table in CUPP_FUNCTION_OP

empty (0)

<operand>

num

Single number

Number in float format

empty (0)

empty (0)

intv

Interval

SPACE

<left bound>

<right bound>

intb

Interval bound

Number in float format
or SPACE if bound is infinite

Type of bound (integer)
1: '='
2: '<'
3: '>'
4: '-inf'
5: 'inf'

empty (0)

Symbolic Terms

sym

Unquoted literal

Character string
(max 32)

length of string

<continuation string>

qlit

Quoted literal

Character string without quotes (max 32)

length of string

<continuation string>

c

Continuation string

String (segment)

length of string

<continuation string>
if length is <= len(OP), this is empty (0)

Variables

var

Symbol used as a variable

Name of variable

empty (0)

empty (0)

avar

Characteristic variable

Internal identifier of characteristic (ATINN)

<instance variable>
(root, parent, self) stored as sym

Flag (RFLAG) for characteristic kind:
aw: single valued
mw: multi valued
azw: restrictable

fvar

Facet variable

Internal identifier of characteristic (ATINN)

<instance variable>
(root, parent, self) stored as sym

Facet identifier:
Invisible: '1'

prd2

Characteristic variable
(R/3 2.2 format)

Avar

<Internal identifier of characteristic> (ATINN) stored as sym

<instance variable>
(root, parent, self) stored as sym

Type Specification

obj

Type specification
(TYPE_OF)

Object type + class type

<object key> stored as sym

empty (0)

Lists

cons

Head of list

Name of list item
(in most cases SPACE)

<list element>
(CAR)

<tail of list>
(CDR)

$nil

Empty list

SPACE

empty (0)

empty (0)

Predicates

prd0

Non-atomic predicate with arity zero
Builtin Examples: true, fail

Name of predicate

empty (0)

empty (0)

prd1

Non-atomic predicate with arity one
Builtin Example: SPECIFIED

Name of predicate

<argument>

empty (0)

prd2

Non-atomic predicate with arity two
Builtin Examples: in_num_set, in_sym_set, TYPE_OF, avar (2.2)

Name of predicate

<argument_1>

<argument_2>

pred

Non-atomic predicate with arity >= three
Builtin Examples: $kbau_set_pricing_factor, $kbau_set_default

Name of predicate

<list of arguments>

empty (0)

Tables

tab

Table call

Internal table identifier (CLINT)

<arguments>

empty (0)

icol

Input argument

Internal identifier of formal argument (ATINN)

<actual argument>

<rest arguments>

ocol

Output argument

Internal identifier of formal argument (ATINN)

<actual argument>

<rest arguments>

dcol

Output argument
(default/soft inference)

Internal identifier of formal argument (ATINN)

<actual argument>

<rest arguments>

rcol

Changed argument

Internal identifier of formal argument (ATINN)

<actual argument>

<rest arguments>
(= 0 at end of arguments list)

Functions

fun

Variant function call
(FUNCTION)

Internal function identifier (CLINT)

<arguments>

empty (0)

pfun

Variant function call
(PFUNCTION - exports root, parent, self)

Internal function identifier (CLINT)

<arguments>

empty (0)

Assignments

sass

Symbolic assignment expression (single valued target)

=

<target>

<source>

nass

Numeric assignment expression (single valued target)

=

<target>

<source>

smas

Symbolic assignment expression (multi valued target)

=

<target>

<source>

mas

Numeric assignment expression (multi valued target)

=

<target>

<source>

sres

Symbolic domain restriction (restrictable target)

=

<target>

<source>

nres

Numeric domain restriction (restrictable target)

=

<target>

<source>

bass

Boolean assignment expression (characteristic facet target)

=

<target_fvar>

<source>

Control Statements

cond

Conditional action

IF

<condition>

<list of actions>

Note: entries in brackets <..> denote references to other terms in the code tree.

Trace Settings

Data

Type

Comments

CUOVD_KBAU_TRC_ON

C

Boolean indicator for 'trace active'

CUOVD_KBAU_MTRC_ON

C

Boolean indicator for 'NEW trace active'

Trace Records

Data

Type

Comments

CUOVD_TRC

Table of CUOVT_TRC_LINE

Table with trace messages + optional detail infos for each message

 

Type CUOVT_TRC_LINE

Field

Type

Description

HANDLE

I

Handle of trace message

MODULE

CUOVT_MODULE Identifier of the module to which the trace message belongs (e.g. CSTR for constraints, DDB for Dynamic Database)

KEY

CUOVT_INT_KEY

Numeric key of trace entry

MSGNR

T100-MSGNR

T100 Message number

CURR_DATA

CUOVT_TRC_DATA

A table with detail info about input and output parameters to dependency processing in the current traced operation
(optional - only recorded for 'detail' trace)

Error Handling

T100 message area: 28. Formroutine for error messages: CUOV_MSG. Global return code variable (CUOVD_RETCODE) is set and an 'S' message is issued.
The message includes the name of the currently processed dependency (KNNAM). Example (28-510): 'Error in dependency processing: division by zero in
dependency &1<KNNAM>'. Messages are also recorded in the application log. They can be displayed via transaction slg1 for object PPVA subobject CUOV.

 

Implementation Details

This section describes implementation details of the dependency processing functions.

 

Overview

Function group CUOV is written in 'old style' (non-Object Oriented) ABAP and can process dependencies against ONE configuration
represented in the Dynamic Database (function group CUDB).

Program SAPLCUOV has the following includes:

Include

Description

LCUOVTOP

Global Data

LCUOVF01

General formroutines for condition action / procedure

LCUOVF02

Evaluation of table/function call

LCUOVF03

Evaluation involving azw variables (restrictable characteristics)

LCUOVF05

Trace handling

LCUOVO01

Trace detail screen

Object Identifiers

  • Dependencies are identified via internal numbers (CUKB-KNNUM - NUMC10)
  • Object Types (Classes/materials) are identified via a triple object type, class type, object key (DDB_ITP - CHAR10/3/50)
  • Characteristics are identified via internal inumbers (CABN-ATINN - NUMC10)
  • Characteristic values are either numeric (CAWN-ATFLV) or symbolic (CAWN-ATWRT)
  • Instances in the configuration are identified via instance numbers (CUINST - NUMC8)

 

Basic Dependency Interpretation Algorithm

The interpreter starts with the root node of the code tree and evaluates it.

  • For conditions, the root node is a condition term
  • For actions and procedures, the root node is a list term with the list items representing simple assignment statements

Evaluating a term means:

  • Calculating a boolean success/failure indicator
  • Possibly calculating additional result fields like e.g. a symbolic value (ATWRT)
  • Possibly generating side effects (value assignments) in the Dynamic Database (DDB)

Based on the term type, calculating these results requires evaluation of one or several child terms in the code tree. Evaluation functions are generally recursive.

For each term type, a specialized evaluation function exists (form routines with naming convention CUOV_EVAL*).

The following table shows evaluation steps for the condition example shown above (Fig. 3.2.1):

Stacklevel

Form routine

Description

Comments

1

CUOV_EVAL_CND 
  • Start to evaluate Term 1
  • Term 1 is identified as a binary logical operator term (OR)

 

2

 CUOV_EVAL_BLOG
  • Start to evaluate first OR condition (Term 2)

 

3

 CUOV_EVAL_CND
  • Term 2 is identified as symbolic comparison expression

 

4

 CUOV_EVAL_SXPR
  • Evaluate first child Term 3 representing the Left Hand Side of the symbolic comparison expression

 

5

 CUOV_EVAL_STERM
  • Term 3 is identified as a characteristic variable term (type = 'avar').
  • Return the current value (eg: 'XYZ') of the variable as retrieved via a read access to the DDB (CUOV_EVAL_AVAR_SINGLE)

The result of this step depends on the content of the configuration (DDB).
The DDB is accessed via function modules in function group CUDB.

4

 CUOV_EVAL_SXPR
  • Evaluate second child Term 4 representing the Right Hand Side of the symbolic comparison expression

 

5

 CUOV_EVAL_STERM
  • Term 4 is identified as a quoted literal (string constant 'XYZ')
  • Return the constant string value 'XYZ'

 

4

 CUOV_EVAL_SXPR
  • Compare the value found for Left Hand Side and Right Hand Side of the symbolic comparison expression
  • Return result (TRUE) of EQ test

 

3

 CUOV_EVAL_CND
  • Return result of this condition

 

2

 CUOV_EVAL_BLOG
  • First OR condition was evaluated to TRUE
  • Finish evaluation of OR condition
  • Return result (TRUE) of OR condition

If the first condition result was FALSE, the evaluation would proceed to evaluate the second OR condition.

1

 CUOV_EVAL_CND
  • Finish evaluation of condition
  • Return result

 

Function Details: CUOV_CHECK_CONDITION

 

Abstract: evaluate a set of pre- or selection conditions.

Import:

  • CNDTYPE: P = precondition, S = selection condition
  • KEY_DATE: validity date for master data access

Export:

  • RESULT: T = True, F = False
  • KNNUM: internal number of dependency that determined the result

Tables:

  • CODE: table with dependency code for one or several dependencies (readonly)

Step

Description

Comments

1

Reset return error code and result dependency KNNUM
Set global variables for validity date and trace module

 

2

Loop at lines of import table CODE: for each dependency (CODE-KNNUM) copy the code lines to local terms table X_CODE

 

3

At each group change in CODE-KNNUM evaluate the current dependency code collected in X_CODE:
for preconditions call formroutine CUOV_EVAL_PRECND(+X_CODE)
for selection conditions call formroutine CUOV_EVAL_SELCND(+X_CODE).
Keep the internal number of the currently evaluated dependency in global variable CUOVD_KNNUM.
Make sure to also process the last KNNUM.

A difference between precondition and selection condition occurs if multiple conditions (KNNUMs) are passed in the CODE table:

  • If a precondition returns false, the remaining preconditions in CODE are not evaluated and a total result 'F' is returned ('stop at first violated precondition').
  • If a selection condition returns true, the remaining selection conditions in CODE are not evaluated and a total result 'T' is returned ('stop at first satisfied selection condition')

3a

CUOV_EVAL_PRECND
CUOV_EVAL_SELCND

Another difference between the two condition types is the way in which the dependency interpreter handles terms that evaluate to result 'UNKNOWN':
A symbolic comparison expression like $ROOT.COLOR = 'RED' evaluates to result UNKNOWN, if no value for COLOR is set in the configuration ('ternary evaluation logic').

  • for a precondition, UNKNOWN is projected to TRUE because there is no proof that the condition is violated
  • for a selection condition, UNKNOWN is projected to FALSE, because there is no proof that the condition is satisfied.
    The background is, that only violated preconditions and satisfied selection conditions cause inferences in the configuration to happen (conflicts or selection of additional objects). With the above logic, no unjustified inferences will occur. Or, in other words, no inferences will be based on the absence of information.
    Issues arising from unknown or NOT SPECIFIED characteristics are similar to the issues with NULL values in the database.

4

Within CUOV_EVAL_PRECND/SELCND the following steps are executed:

 

4a

basic health check on code

Code must be non-empty

4b

Determine whether tracing is requested for the current dependency (CUOV_CHECK_KBAU_TRC).
This information is needed to record varaible bindings that occur during dependency evaluation. For performance reasons this recording is only done if trace is switched on.

Calls out to trace function modules like CUTC_MSG_NEEDED

4c

Perform generic condition evaluation with ternary result logic including UNKNOWN (CUOV_EVAL_CND).

Formroutine recursively evaluates the code terms as described in Chapter 4.3.

4d

Collect trace data and store them as trace message (possibly with details about variable bindings) in the trace module (CUOV_HANDLE_KBAU_TRC)

Calls out to trace function module CUTC_SET_MSGX_TXT

Function Details: CUOV_DO_PROCEDURE

 

Abstract: evaluate a sequence of procedures. Import:

  • KEY_DATE: validity date for master data access Tables:
  • CODE: table with dependency code for one or several dependencies (readonly) Exceptions:
  • ACTION_DONE: indicates that a change was made to the DDB
  • INTERNAL_ERROR: an internal (hard) error occurred
  • UNKNOWN_INSTANCE: an inference was attempted on an unknown DDB instance

Step

Description

Comments

1

Reset return error code and flag for 'action done'.
Clear variable for 'currently processed dependency' (CUOVD_KNNUM).
Set global variables for validity date and trace module.

 

2

Prepare global variable for justification used for procedure inferences in the DDB (CUOVD_JUSTIFICAND).

A justification identifies a 'reason' for a value assignment in the DDB and is used in the overwrite logic of the DDB and in the explanation functions.
The fields 'KNTYPE' (knowledge type) and SEGM ('knowledge segment') have the same constant values for all procedure inferences.
The field AUTHOR is set to the internal number of the procedure (CUOVD_KNNUM).

3

Loop at lines of import table CODE: for each dependency (CODE-KNNUM) copy the code lines to local terms table X_CODE

It is crucial, that the given sort order of procedures is preserved.

4

At each group change in CODE-KNNUM evaluate the current dependency code collected in X_CODE:
for procedures and actions we call formroutine CUOV_EVAL_ACTIONS(+X_CODE)
Keep the internal number of the currently evaluated dependency in global variable CUOVD_KNNUM.
Make sure to also process the last KNNUM.

 

4

Within CUOV_EVAL_ACTIONS the following steps are executed:

 

4a

Determine whether tracing is requested for the current dependency (CUOV_CHECK_KBAU_TRC).
This information is needed to record variable bindings that occur during dependency evaluation. For performance reasons this recording is only done if trace is switched on.

Calls out to trace function modules like CUTC_MSG_NEEDED

4b

Perform generic procedure statement evaluation (CUOV_EVAL_ACTION_LIST).

Formroutine recursively evaluates the code terms as described in Chapter 4.3.
The code of a procedure has the form of a 'list of statements'.

4c

Each statement is evaluated in formroutine CUOV_EVAL_ACTION.

A procedure statement can be a simple assignment statement, a multiple assignment statement, a domain restriction, a facet assignment, an IF-THEN (conditional) statement, a variant table or variant function statement or a general builtin function statement (e.g. $set_default, $set_pricing_factor) .
Inferences (value assignments) are immediately applied to the DDB using function modules in function group CUDB.
The function calls for value assignment are wrapped in formroutine CUOV_SET_VAL.

4d

Collect trace data and store them as trace message (possibly with details about variable bindings) in the trace module (CUOV_HANDLE_KBAU_TRC)

Calls out to trace function module CUTC_SET_MSGX_TXT

5

Check if a change was made on the DDB. If this is the case (CUOVD_ACTION_DONE = T), the exception ACTION_DONE is raised.

The exception seems like a slightly awkward mechanism to convey 'positive information' - a better approach might be to use a simple return code/flag as EXPORTING parameter..

Comment: A complete 're-evaluation' cycle for procedures includes the removal of all previously known procedure inferences BEFORE calling this function.
The removal step is done in high level configuration using function module CUDB_DEL_ATTRS_BY_KNTYPE (called e.g. in CEI0 formroutine TMS_PROCEDURE).
The removal step is necessary to guarantee reproducible results of the procedure evaluation in case a configuration is checked multiple times.

 

Function Details: CUOV_DO_ACTION

Abstract: evaluate a sequence of actions. Import:

  • KEY_DATE: validity date for master data access Tables:
  • CODE: table with dependency code for one or several dependencies (readonly) Exceptions:
  • ACTION_DONE: indicates that a change was made to the DDB
  • INTERNAL_ERROR: an internal (hard) error occurred
  • UNKNOWN_INSTANCE: an inference was attempted on an unknown DDB instance

The steps executed in this function are very similar to the steps in CUOV_DO_PROCEDURE. The following differences exist:

2

Prepare global variable for justification used for procedure inferences in the DDB (CUOVD_JUSTIFICAND).

The fields 'KNTYPE' (knowledge type) and SEGM ('knowledge segment') have the constant values for action inferences and are different from the corresponding values for procedures.
The system must be able to distinguish procedure justifications from action justifications.

4c

Each statement is evaluated in formroutine CUOV_EVAL_ACTION.

Inferences (value assignments) are immediately applied to the DDB using function modules in function group CUDB.
The function calls for value assignment are wrapped in formroutine CUOV_SET_VAL.

Within CUOV_SET_VAL, a different DDB function is called for actions than for procedures:

  • For procedures CUDB_REPL_VAL is called because procedures can overwrite each other
  • For actions CUDB_SET_VAL is called because actions cannot overwrite each other (two different action inferences for the same characteristic
    cause a value conflict)|

Comment: A complete 're-evaluation' cycle for actions includes the removal of all previously known action inferences BEFORE calling this function.
The removal step is done in high level configuration using function module CUDB_DEL_ATTRS_BY_KNTYPE (called e.g. in CEI0 formroutine TMS_ACTION).
The removal step is necessary to guarantee reproducible results of the action evaluation in case a configuration is checked multiple times..
Within a re-evaluation cycle, the same set of actions can be evaluated multiple times because the variant configurator attempts to calculate all
possible inferences from the actions independent of their sort order ('DO 25 TIMES').

 

Function Details: CUOV_SET_OVARS

Abstract: set runtime bindings for object variables $self, $parent, $root. Import:

  • PARENT: identifier (NUMC8) of the parent instance of the currently configured DDB instance
  • ROOT: identifier (NUMC8) of the root instance in the current configuration
  • SELF: identifier (NUMC8) of the currently configured DDB instance Exceptions:
  • INTERNAL_ERROR: an internal (hard) error occurred

Comment:

This function must be called before calling CUOV_DO_PROCEDURES/ACTIONS or CUOV_CHECK_CONDITION so that the dependency interpreter
knows against which DDB instances it should resolve syntax elements involving the object variables $self, $parent, $root ( e.g. $self.COLOR = 'RED').

  • In a single level (one instance) configuration, $self = $root = $parent = 1.
    • Note: $self = $parent is a rather arbitrary convention in this case
  • In a multi-level configuration, the focus of dependency evaluation shifts from one instance to the next through the BOM parts hierarchy as the configuration
    check proceeds. CUOV_SET_VARS is called whenever a focus shift happens.
    • It's an implicit convention that $root is always =1
  • For evaluation of a BOM item selection condition, $self denotes the part instance that may or may not be created via the selection condition.
    Strictly speaking, $self is undefined for BOM item selection conditions because the condition is evaluated BEFORE instantating the part.
    • Special master data references like MDATA $SELF.STPO_POSNR are nevertheless allowed in this case to allow for a 'generic' modelling
      of selection conditions

 

Tips&Tricks for Debugging

Explanation

The variant configurator has an explanation function to provide details about the current state of the configuration. If you see a value that
was calculated by the configurator you can obtain an explanation for this value by clicking on the 'info' button behind the value:

Fig: CU50 Explanation of a calculated characteristic value

 

The system will show a popup with all 'reasons' or 'justification's of the value. You can also double click one the of the justifications to obtain
more detailed information like e.g. the documentation & source code of a dependency.

Trace

Evaluation of classic dependencies can be debugged with the help of the variant configurator trace function. In the configuration screen
(va01/cu50) go to menu 'Extras -> Trace -> Settings' and switch on the configurator trace for one or several of the following trace areas:

  • Preconditions
  • Selection conditions
  • Actions
  • Procedures
  • Dynamic database

 

Fig: cu50 Define Trace Settings

Check the corresponding check boxes in column 1 and activate your selection. In the filter dialog you can specify a list of objects (dependencies)
to which tracing should be applied - this is useful to limit the size of trace outputs in large configuration models.

Perform the configuration steps you want to investigate and then goto menu 'Extras->Trace->Display' to view the trace messages recorded.

Fig: cu50 - Display recorded Trace Messages.

This figure shows a set of trace messages recorded at the 'more detailed' level: the list shows which dependencies have been evaluated and
includes information about input ('>') and output ('>') parameters of procedures. By double clicking on a trace message for a dependency you
can display its source code. Typical errors like missing inferences can be analyzed by looking e.g. at the input values to procedures and
actions in this list.

Logging

Messages about serious errors like corrupt code or zero divisions encountered during dependency evaluation are written to the application log
using function module CUTC_WRITE_APPL_LOG. These messages can be viewed in transaction slg1 for object 'PPVA' and subobject 'CUOV'.

Break-Points

Logical step

Code location

Create a logged message

Formroutine CUOV_MSG

Evaluate procedures

Function CUOV_DO_PROCEDURE, first line,
Possibly add a watch-point on CUOVD_KNNUM

 

If you want to filter to a particular dependency, you can also switch on filtered trace for this dependency and place a break-point
in CUOV_CHECK_KBAU_TRC on the line with CUOVD_KBAU_TRC_ON = TRUE.

Evaluate a procedure/action statement

Formroutine CUOV_EVAL_ACTION

Get a value from the Configuration

Formroutine CUOV_GET_VAL

Set a value in the Configuration

Formroutine CUOV_SET_VAL

Get a master data (MDATA) value

Formroutine CUOV_EVAL_MASTER_DATA

Evaluate preconditions /selection conditions

Function CUOV_CHECK_CONDITION, first line,
Possibly add a watch-point on CUOVD_KNNUM

Evaluate variant table access

Formroutine CUOV_EVAL_TABLE

Evaluate variant function call

Formroutine CUOV_EVAL_FUNCTION

 

 

OSS Notes

The following table gives an overview of OSS notes about classic dependency evaluation. Main component for notes search: LO-VC-DEP. Keywords: SAPLCUOV
Priorities give the author's personal view of how important a note is (1=very high, 2=high, 3=medium). Prio = MOD indicates modification notes. OSS notes with
numbers <500000 are usually old and should be available in most customer systems.

Topic

Number

Title

Comment

General

 

977372

Dependencies corrupt after Unicode conversion

Maintenance issue

 

917987

General performance in variant configuration

Consulting

 

670571

Object dependencies are processed incorrectly

Fixed in 4.5B

 

 

 

 

Pre/Selection Conditions

 

961910

Mandatory characteristics and preconditions

MOD, Pilot release

 

544523

LO-VC-DEP: Error with conditions with multi-value characteristics

Fixed in 4.6C SP36, 4.7 SP02

 

359733

Rounding error in value check with intervals

Fixed in 4.6C SP13

 

307786

Performance: MDATA and multi-value characteristics

 

 

128247

Ref MDATA $SELF.<Characteristic> in select conditn

 

 

 

 

 

Procedure

 

718257

Error in dependency: negative value for characteristic

 

 

398350

Optional output parameters for variant functions

 

 

183548

Object dependencies: indicator 'Negative values allowed'

 

 

173918

Rounding error in requirements with IN operator

'Requirements' should be called 'dependencies'

 

166766

Error in CEIL,TRUNC,FRAC functions in obj.dependncs

Consulting

 

90417

Default values in object dependencies

MOD

Explanation & Trace

 

567263

CU50:Explanatn for dependency causes exceptn CONVT_OVERFLOW

Bug in pretty printer

 

480738

Trace output for configuration is lost

Fixed in 4.6C SP28

 

387703

Detail trace for restrict. charact. in object dependencies

 

 

 

 

  • No labels