trilib04.gms : Demonstrates problems with a stateful function library

**Description**

This demonstrates the problems with a stateful function library in the context of GAMS and solver processes. The trilib default mode for computations is in radians (mode=0). The function SetTriMode can be used to interpret the arguments of subsequent function calls to Cosine and Sine as degrees (mode=1) instead of radians (mode=0). The SetTriMod function returns the previous mode value. Contributor: Michael Bussieck

**Small Model of Type : ** GAMS

**Category :** GAMS Test library

**Main file : ** trilib04.gms **includes : ** compilec.inc [html] precomp.inc [html]

```
$Title Demonstrates problems with a stateful function library (TRILIB04,SEQ=552)
$ontext
This demonstrates the problems with a stateful function library in
the context of GAMS and solver processes.
The trilib default mode for computations is in radians (mode=0). The
function SetTriMode can be used to interpret the arguments of
subsequent function calls to Cosine and Sine as degrees (mode=1)
instead of radians (mode=0). The SetTriMod function returns the
previous mode value.
Contributor: Michael Bussieck
$offtext
$ifThen set nocomp
* Use precompiled library provided by testlib
$ batinclude precomp.inc tricclib
$else
* Compile library from source code
$ batinclude compilec.inc tri
$endIf
function mySetTriMode / myLib.SetTriMode /
myCos / myLib.Cosine /;
variable x, y; equation e;
e.. x =e= mycos(y);
model m /e/;
* Everything is default, so in radians
y.fx = pi/2;
solve m min x using nlp;
abort$(abs(x.l-0)>1e-12) 'x<>0';
display$mySetTriMode(1) 'Now we switch to degrees but do solvelink=ChainScript';
* The solver runs in a separate process and we start with a new function library instance with default state (i.e. mode=0)
m.solvelink=%solvelink.ChainScript%;
solve m min x using nlp;
abort$(abs(x.l-0)>1e-6) 'x.l expected to be 0', x.l;
* Since GAMS solve restarts with a new process and a default state library mode was 0
abort$(0<>mySetTriMode(1)) 'mode expected to be 0';
* Now the same with solvelink=CallModule, where we have a solver process, but GAMS stays memory resident
m.solvelink=%solvelink.CallModule%;
solve m min x using nlp;
abort$(abs(x.l-0)>1e-6) 'x.l expected to be 0', x.l;
abort$(1<>mySetTriMode(1)) 'mode expected to be 1';
* Now the same with solvelink=LoadLibrary, where we have a solver library linked into GAMS
m.solvelink=%solvelink.LoadLibrary%;
y.fx=90;
solve m min x using nlp;
abort$(abs(x.l-0)>1e-6) 'x.l expected to be 0', x.l;
abort$(1<>mySetTriMode(1)) 'mode expected to be 1';
```