# A Soft Limiter

This is a definition for a soft limiter device. This will pass the input signal through unchanged up to some limit after which it will follow a decaying exponential in the form:

`1 - exp( -(v-vlim) )`

The same in reverse occurs for the lower limit. Here is the full definition:

```'include "disciplines.vams"
module soft_limiter(in, out) ;

electrical in, out ;
parameter real  vlow=-1.0,
vhigh=1.0,
soft=0.1 from (0:1.0) ;

localparam real band = (vhigh-vlow)*soft,
vlow_1 = vlow+band,
vhigh_1 = vhigh-band ;

real vin ;

analog
begin

@(initial_step)
if (vhigh<vlow)
begin
\$strobe("Lower limit must be less than higher limit") ;
\$finish ;
end

vin = V(in) ;

if (vin>vhigh_1)
V(out) <+ vhigh_1+band*(1.0-exp(-(vin-vhigh_1)/band));
else if (vin<vlow_1)
V(out) <+ vlow_1-band*(1.0-exp((vin-vlow_1)/band)) ;
else
V(out) <+ vin ;
end
endmodule```

See Examples/Manual/Soft-limiter example

The above example introduces the following new concepts:

1. Variables. We use vin to hold the value of V(in). In this example we have done this simply to make the code a little more readable. But variables can store any value or expression and have a much wider use
3. The exp function
4. Local parameters using the localparam keyword
5. Parameter value range limits using the from keyword. (Also used in the resistor previous)

The soft limit example also uses a conditional statements using if and else which we first saw with the resistor example above.

In this topic:

## Variables

Variables, such as vin in the example must be declared first. In the above example this declaration is the line:

`real vin ;`

This declares the variable 'real'. This is 'real' in the computing sense meaning that the value is stored using floating point arithmetic and can take non-integer values. The alternative declaration is integer which means the variable stores whole numbers. Variable declarations, like parameter declarations must be placed within the module - endmodule block. They can be declared outside the analog block, as in the example above, or they can be declared inside a named begin - end block. For example

```begin : main
real vin ;
...
end```

If declared this way, the variable may only be used within the begin - end block in which it was declared.

## \$finish

The \$finish system task aborts the simulation unconditionally.

## Functions

Verilog-A has a range of mathematical functions built-in. In the above example we have used the exp function. See Verilog-A Functions for a complete list.

## Local Parameters

A local parameter is one that cannot be changed by the user via the .MODEL statement or any other means. Local parameters are a way of defining constant vaues as, unlike variables, they cannot be assigned except in their declaration. In our example we declared the band local parameter as:

`localparam real band = (vhigh-vlow)*soft`

We could just as simply have defined a variable to do this. However, by using a local parameter we know it can't be subsequently modified. This aids readability but more importantly tells the compiler that it cannot change allowing to optimise the result effectively.

## Parameter Limits

Parameters can be given maximum and minimum limits. This is done using the from keyword. In the above example:

`soft=0.1 from (0:1.0)`

defines the limits for soft from 0 to 1.0 exclusive. This means that any value greater than 0 and less than 1.0 will be accepted but the values 0 and 1.0 will not be allowed. You can also define inclusive limits using a square bracket instead of a round parenthesis. E.g in the following 1.0 is allowed:

`soft=0.1 from (0:1.0]`

## Conditional Statements

Conditional statements are in the form:

```if (conditional-expression)
statement ;
else
statement ;```

statement may be a single statement such as a branch contribution or it may be a collection of statements enclosed by begin and end.