/[ascend]/trunk/base/generic/solver/analyze.c
ViewVC logotype

Diff of /trunk/base/generic/solver/analyze.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 218 by johnpye, Mon Jan 16 08:53:30 2006 UTC revision 219 by johnpye, Wed Jan 25 07:41:58 2006 UTC
# Line 1  Line 1 
1  /*  /*
2   *  Problem Analysis Routines      Problem Analysis Routines
3   *  by Benjamin Andrew Allan      by Benjamin Andrew Allan
4   *  5/19/96      5/19/96
5   *  Version: $Revision: 1.56 $      Version: $Revision: 1.56 $
6   *  Version control file: $RCSfile: analyze.c,v $      Version control file: $RCSfile: analyze.c,v $
7   *  Date last modified: $Date: 2003/08/23 18:43:12 $      Date last modified: $Date: 2003/08/23 18:43:12 $
8   *  Last modified by: $Author: ballan $      Last modified by: $Author: ballan $
9   *  Copyright(C) 1996 Benjamin Andrew Allan      Copyright(C) 1996 Benjamin Andrew Allan
10   *  
11   *  This file is part of the ASCEND IV math programming system.      This file is part of the ASCEND IV math programming system.
12   *  
13   *  The SLV solver is free software; you can redistribute      The SLV solver is free software; you can redistribute
14   *  it and/or modify it under the terms of the GNU General Public License as      it and/or modify it under the terms of the GNU General Public License as
15   *  published by the Free Software Foundation; either version 2 of the      published by the Free Software Foundation; either version 2 of the
16   *  License, or (at your option) any later version.      License, or (at your option) any later version.
17   *  
18   *  The SLV solver is distributed in hope that it will be      The SLV solver is distributed in hope that it will be
19   *  useful, but WITHOUT ANY WARRANTY; without even the implied warranty of      useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
20   *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
21   *  General Public License for more details.      General Public License for more details.
22   *  
23   *  You should have received a copy of the GNU General Public License      You should have received a copy of the GNU General Public License
24   *  along with the program; if not, write to the Free Software Foundation,      along with the program; if not, write to the Free Software Foundation,
25   *  Inc., 675 Mass Ave, Cambridge, MA 02139 USA.  Check the file named      Inc., 675 Mass Ave, Cambridge, MA 02139 USA.  Check the file named
26   *  COPYING.  COPYING is found in ../compiler.      COPYING.  COPYING is found in ../compiler.
27   *  */
28   *  
29   *  These functions are the start of a new design for feeding  /** @file analyze.c
30   *  solvers from the ASCEND compiler or any arbitrary backend.  
31   *      These functions are the start of a new design for feeding
32   *  The intention is that eventually the other code in the solver      solvers from the ASCEND compiler or any arbitrary backend.
33   *  directory will really be for *solution algorithms* and the  
34   *  definition of a *problem* will come from here. In essence, most      The intention is that eventually the other code in the solver
35   *  of what was solver/system.c will be here. Negotiating directly      directory will really be for *solution algorithms* and the
36   *  with the ASCEND instance hierarchy should not be a solver's      definition of a *problem* will come from here. In essence, most
37   *  job.      of what was solver/system.c will be here. Negotiating directly
38   *  The goal of this module is to CREATE a slv_system_t data structure      with the ASCEND instance hierarchy should not be a solver's
39   *  capable of supporting code generation, an interactive interface, and      job.
40   *  in-core solvers, while being expandable in the future to out of core      The goal of this module is to CREATE a slv_system_t data structure
41   *  solvers/external-process solvers.      capable of supporting code generation, an interactive interface, and
42   *      in-core solvers, while being expandable in the future to out of core
43   *  A secondary goal is to have nonlinear solver files be independent of      solvers/external-process solvers.
44   *  all the compiler directory files except ascmalloc.h.  
45   *  The present fly in the ointment is expr.h because of the objective fcns.      A secondary goal is to have nonlinear solver files be independent of
46   *  The relman and exprman modules go away because they are indicative of      all the compiler directory files except ascmalloc.h.
47   *  functionality that belongs either in the compiler or rel.c.      The present fly in the ointment is expr.h because of the objective fcns.
48   *  If we meet this goal, then it is a simple matter to connect any      The relman and exprman modules go away because they are indicative of
49   *  arbitrary compiler backend to the solver API by replacing the rel      functionality that belongs either in the compiler or rel.c.
50   *  and var and analyze modules.      If we meet this goal, then it is a simple matter to connect any
51   *      arbitrary compiler backend to the solver API by replacing the rel
52   */      and var and analyze modules.
53    */
54    
55  #include <stdarg.h>  #include <stdarg.h>
56  #include "utilities/ascConfig.h"  #include "utilities/ascConfig.h"
# Line 116  static symchar *g_strings[3]; Line 117  static symchar *g_strings[3];
117    
118    
119  /*  /*
120   * Forward declaration      Forward declaration
121   */   */
122  static void ProcessModelsInWhens(struct Instance *, struct gl_list_t *,  static void ProcessModelsInWhens(struct Instance *, struct gl_list_t *,
123                                   struct gl_list_t *, struct gl_list_t *);                                   struct gl_list_t *, struct gl_list_t *);
124    
125  /*  /*
126   * Global variable. Set to true by classify if need be      Global variable. Set to true by classify if need be
127   */   */
128  static int g_bad_rel_in_list;  static int g_bad_rel_in_list;
129    
# Line 133  struct gl_list_t *g_symbol_values_list = Line 134  struct gl_list_t *g_symbol_values_list =
134  struct varip {  struct varip {
135    struct var_variable *data;  /* ptr to destination of data */    struct var_variable *data;  /* ptr to destination of data */
136    int index;              /* master gl index */    int index;              /* master gl index */
137    int incident;           /* set 0 in classify_instance,    int incident;           /* set 0 in classify_instance, 1 make_master_lists */
                  1 make_master_lists */  
138    int in_block;           /* set 0 in classify_instance */    int in_block;           /* set 0 in classify_instance */
139    int fixed;              /* set in classify_instance */    int fixed;              /* set in classify_instance */
140    int solvervar;          /* set in classify_instance */    int solvervar;          /* set in classify_instance */
141    int active;                 /* is this var a part of my problem */    int active;             /* is this var a part of my problem */
142    int basis;                  /* set in classify_instance */    int basis;              /* set in classify_instance */
143  };  };
144    
145    
146  struct disvarip {  struct disvarip {
147    struct dis_discrete *data;    /* ptr to destination of data */    struct dis_discrete *data;    /* ptr to destination of data */
148    int index;                /* master gl index */    int index;                    /* master gl index */
149    int fixed;                /* set in classify_instance */    int fixed;                    /* set in classify_instance */
150    int isconst;                  /* is this dis var constant ? */    int isconst;                  /* is this dis var constant ? */
151    int distype;                  /* 0 boolean, 1 int, -1 symbol */    int distype;                  /* 0 boolean, 1 int, -1 symbol */
152    int value;                    /* integer value of the variable */    int value;                    /* integer value of the variable */
# Line 160  struct disvarip { Line 160  struct disvarip {
160  struct relip {  struct relip {
161    struct rel_relation *data;    /* ptr to destination of data */    struct rel_relation *data;    /* ptr to destination of data */
162    long model;       /* relation is in this model in model gllist */    long model;       /* relation is in this model in model gllist */
163              /* set in CollectRelsAndWhens. = 1.. nmodels */                      /* set in CollectRelsAndWhens. = 1.. nmodels */
164                          /* rel_relation models = u.r.model-1 */                      /* rel_relation models = u.r.model-1 */
165    int index;        /* master gl list index */    int index;        /* master gl list index */
166    int obj;  /* is it an objective relation. set in classify_instance */    int obj;          /* is it an objective relation. set in classify_instance */
167    int ext;  /* is it e_blackbox. set in classify_instance */    int ext;          /* is it e_blackbox. set in classify_instance */
168    int included; /* set in classify_instance */    int included;     /* set in classify_instance */
169    int cond; /* is it a conditional relation. set in classify_instance */    int cond;         /* is it a conditional relation. set in classify_instance */
170    int inwhen;   /* is it in a when */    int inwhen;       /* is it in a when */
171    int active;   /* is this rel a part of my problem */    int active;       /* is this rel a part of my problem */
172  };  };
173    
174  struct logrelip {  struct logrelip {
175    struct logrel_relation *data;    /* ptr to destination of data */    struct logrel_relation *data;    /* ptr to destination of data */
176    long model;       /* logrelation is in this model in model gllist */    long model;   /* logrelation is in this model in model gllist */
177    int index;        /* master gllist index */    int index;    /* master gllist index */
178    int included;         /* set in classify_instance */    int included; /* set in classify_instance */
179    int cond; /* is it a conditional logrelation.  */    int cond;     /* is it a conditional logrelation.  */
180    int inwhen;   /* is it in a when */    int inwhen;   /* is it in a when */
181    int active;   /* is this logrel a part of my problem */    int active;   /* is this logrel a part of my problem */
182  };  };
183    
184  struct whenip{  struct whenip{
185    struct w_when *data;   /* ptr to destination of data */    struct w_when *data;  /* ptr to destination of data */
186    long model;            /* when is in this model in model gllist */    long model;           /* when is in this model in model gllist */
187    int index;         /* master gllist index */    int index;            /* master gllist index */
188    int inwhen;            /* is it in a when */    int inwhen;           /* is it in a when */
189  };  };
190    
191  struct modip {  struct modip {
192    int index;        /* set in make master lists. 1..nmodels */    int index;        /* set in make master lists. 1..nmodels */
193    int inwhen;           /* is it in a when */    int inwhen;       /* is it in a when */
194  };  };
195    
196  /* we will decorate the ascend instance tree with these in the interface  /* we will decorate the ascend instance tree with these in the interface
197   * pointers, but ONLY for the system build process and not persistently.      pointers, but ONLY for the system build process and not persistently.
198   * DO NOT EVER UNDER ANY CIRCUMSTANCES EXPORT THIS DATA STRUCTURE.      DO NOT EVER UNDER ANY CIRCUMSTANCES EXPORT THIS DATA STRUCTURE.
199   */  */
200  struct solver_ipdata {  struct solver_ipdata {
201    struct Instance *i; /* the kind of instance is the enum for union */    struct Instance *i; /* the kind of instance is the enum for union */
202    union {    union {
# Line 213  struct solver_ipdata { Line 213  struct solver_ipdata {
213  #define SIP(x) ((struct solver_ipdata *)(x))  #define SIP(x) ((struct solver_ipdata *)(x))
214    
215  /*  /*
216   * a bridge buffer used so much we aren't going to free it, just reuse it      a bridge buffer used so much we aren't going to free it, just reuse it
217   */  */
218  static struct reuse_t {  static struct reuse_t {
219    size_t ipcap;         /* number of ips allocated in ipbuf */    size_t ipcap;         /* number of ips allocated in ipbuf */
220    size_t ipused;        /* number of ips in use */    size_t ipused;        /* number of ips in use */
# Line 222  static struct reuse_t { Line 222  static struct reuse_t {
222  } g_reuse = {0,0,NULL};  } g_reuse = {0,0,NULL};
223    
224  /*  /*
225   *  a data structure for bridge building only. hell of a scaffolding.      a data structure for bridge building only. hell of a scaffolding.
226   *  all fields should be empty if construction is not in progress.      all fields should be empty if construction is not in progress.
227   *  In particular, do no operations that can throw an exception      In particular, do no operations that can throw an exception
228   *  while manipulating a problem_t, as it is way too big to let leak.      while manipulating a problem_t, as it is way too big to let leak.
229   */  */
230  struct problem_t {  struct problem_t {
231  /* the following are established by CountStuffInTree */  /* the following are established by CountStuffInTree */
232    long nv;      /* number of solvervar/solveratom */    long nv;              /* number of solvervar/solveratom */
233    long np;      /* number of real ATOM instance parameters */    long np;              /* number of real ATOM instance parameters */
234    long nu;      /* number of real ATOM instance uninteresting */    long nu;              /* number of real ATOM instance uninteresting */
235    long ndv;             /* number of discrete variables */    long ndv;             /* number of discrete variables */
236    long nud;             /* number of uninteresting discretes */    long nud;             /* number of uninteresting discretes */
237    long nc;      /* number of conditional relations */    long nc;              /* number of conditional relations */
238    long ncl;     /* number of conditional logrelations */    long ncl;              /* number of conditional logrelations */
239    long nr;      /* number of algebraic relations */    long nr;              /* number of algebraic relations */
240    long no;      /* number of objective rels */    long no;              /* number of objective rels */
241    long nl;      /* number of logical rels */    long nl;              /* number of logical rels */
242    long nw;              /* number of whens */    long nw;              /* number of whens */
243    long ne;      /* number of external rels subset overestimate*/    long ne;              /* number of external rels subset overestimate*/
244    long nm;      /* number of models */    long nm;              /* number of models */
245  /*  /*
246   * The following gllists contain pointers to interface ptrs as      The following gllists contain pointers to interface ptrs as
247   * locally defined.      locally defined.
248   * The lists will be in order found by a visit instance tree.      The lists will be in order found by a visit instance tree.
249   */  */
250    struct gl_list_t *vars;   /* solvervar/solveratom. varips */    struct gl_list_t *vars;   /* solvervar/solveratom. varips */
251    struct gl_list_t *pars;   /* real ATOM instance parameters */    struct gl_list_t *pars;   /* real ATOM instance parameters */
252    struct gl_list_t *unas;   /* real ATOM instance of no 'apparent' use */    struct gl_list_t *unas;   /* real ATOM instance of no 'apparent' use */
253    struct gl_list_t *models; /* models in tree. modips */    struct gl_list_t *models; /* models in tree. modips */
254  /*  /*
255   * The following gllists contain pointers to interface ptrs as      The following gllists contain pointers to interface ptrs as
256   * locally defined.      locally defined.
257   * The lists will be in order found by running over the models list.      The lists will be in order found by running over the models list.
258   */  */
259    struct gl_list_t *dvars;  /* discrete variables */    struct gl_list_t *dvars;  /* discrete variables */
260    struct gl_list_t *dunas;  /* discrete variables of no use */    struct gl_list_t *dunas;  /* discrete variables of no use */
261    struct gl_list_t *whens;  /* whens */    struct gl_list_t *whens;  /* whens */
# Line 275  struct problem_t { Line 275  struct problem_t {
275  /* stuff that should move elsewhere, but end up in slv_system_t */  /* stuff that should move elsewhere, but end up in slv_system_t */
276    mtx_region_t *blocks;     /* array of partitions in reordered matrix */    mtx_region_t *blocks;     /* array of partitions in reordered matrix */
277    int32 nblocks;        /* size of array of partitions */    int32 nblocks;        /* size of array of partitions */
278    int nnz;          /* free nonzeros in processed jacobian */    int nnz;              /* free nonzeros in processed jacobian */
279    int nnztot;           /* total nonzeros in processed relations */    int nnztot;           /* total nonzeros in processed relations */
280    int nnzobj;           /* total nonzeros in objective gradients */    int nnzobj;           /* total nonzeros in objective gradients */
281    int nnzcond;          /* total nonzeros in conditional relations */    int nnzcond;          /* total nonzeros in conditional relations */
# Line 283  struct problem_t { Line 283  struct problem_t {
283    int relincinuse;      /* incidence given to relations so far */    int relincinuse;      /* incidence given to relations so far */
284    int varincsize;       /* total nonzeros in gradients (redundant) */    int varincsize;       /* total nonzeros in gradients (redundant) */
285    int varincinuse;      /* incidence given to variables so far */    int varincinuse;      /* incidence given to variables so far */
286    int ncol;         /* free and incident vars */    int ncol;             /* free and incident vars */
287    int nrow;         /* included relations */    int nrow;             /* included relations */
288    /* conditional stuff */    /* conditional stuff */
289    int32 need_consistency;   /* Conistency analysis is required ? */    int32 need_consistency;   /* Conistency analysis is required ? */
290   /* logical relation stuff */   /* logical relation stuff */
291    int lognnz;           /* Summ of free boolean vars in inc logrels */    int lognnz;           /* Summ of free boolean vars in inc logrels */
292    int lognrow;          /* included logrelations */    int lognrow;          /* included logrelations */
293    int logncol;          /* free and incident boolean vars */    int logncol;          /* free and incident boolean vars */
294    int lrelinc;                  /* incident boolean vars */    int lrelinc;          /* incident boolean vars */
295    int lrelincsize;          /* Total summ of incidences (boolean vars)    int lrelincsize;      /* Total summ of incidences (boolean vars)
296                     in logrels*/                             in logrels*/
297    int lrelincinuse;     /* incidence given to log relations so far */    int lrelincinuse;     /* incidence given to log relations so far */
298  /* data to go to slv_system_t */  /* data to go to slv_system_t */
299    struct rel_relation *reldata;      /* rel data space, mass allocated */    struct rel_relation *reldata;      /* rel data space, mass allocated */
# Line 340  struct problem_t { Line 340  struct problem_t {
340  };  };
341  /* we are making the ANSI assumption that this will be init to 0/NULL*/  /* we are making the ANSI assumption that this will be init to 0/NULL*/
342  /*  /*
343   * container for globals during assembly.      container for globals during assembly.
344   * At present, the mastervl and solvervl are of the same length. This      At present, the mastervl and solvervl are of the same length. This
345   * is purely coincidental and the long run intent is that there is one      is purely coincidental and the long run intent is that there is one
346   * master list and that a problem coordinator would set up the      master list and that a problem coordinator would set up the
347   * solver var/rel lists blockwise as we go along. We may want to put      solver var/rel lists blockwise as we go along. We may want to put
348   * block information in the rel/var structures.      block information in the rel/var structures.
349   */  */
350    
351    
352  /*  /*
353   * The intent here is to do away with the old persistent interface pointer      The intent here is to do away with the old persistent interface pointer
354   * scheme by making the struct rel_relation *individually keep track of the      scheme by making the struct rel_relation* individually keep track of the
355   * map between the ascend RelationVariable list position and the      map between the ascend RelationVariable list position and the
356   * solver's var list index (and hence the column in jacobian for jacobian      solver's var list index (and hence the column in jacobian for jacobian
357   * involved clients).      involved clients).
358   * In this mapping each struct relation * has its var list and this list      In this mapping each struct relation* has its var list and this list
359   * may contain RealAtomInstances that we don't consider variables.      may contain RealAtomInstances that we don't consider variables.
360   * In the rel_relation we will have the variable index list      In the rel_relation we will have the variable index list
361   * which is an array of int32 the same length as the RelationVariable list.      which is an array of int32 the same length as the RelationVariable list.
362   * In the array position 0 corresponds to RelationVariable 1 since the      In the array position 0 corresponds to RelationVariable 1 since the
363   * compiler uses gl_lists. If in the variable index list we encounter      compiler uses gl_lists. If in the variable index list we encounter
364   * a number < 0 we know that that RelationVariable doesn't map to what      a number < 0 we know that that RelationVariable doesn't map to what
365   * we consider a solver variable.      we consider a solver variable.
366   *  
367   * In the near future we may also add to the struct rel_relation *an array,      In the near future we may also add to the struct rel_relation *an array,
368   * a, of int32 pairs like so:      a, of int32 pairs like so:
369   * vlindex | rvindex | vlindex | rvindex      vlindex | rvindex | vlindex | rvindex
370   * and a length. This array could be built of the data for vars that pass      and a length. This array could be built of the data for vars that pass
371   * a filter provided by the client. This way a client could help us avoid      a filter provided by the client. This way a client could help us avoid
372   * having to do if testing while stuffing jacobians.      having to do if testing while stuffing jacobians.
373   * In this scheme stuffing a jacobian row (or whatever) would simply mean      In this scheme stuffing a jacobian row (or whatever) would simply mean
374   * calling the compiler's derivative function (wrt RelationVariable list)      calling the compiler's derivative function (wrt RelationVariable list)
375   * which returns a vector d of values and then doing a loop:      which returns a vector d of values and then doing a loop:
376   *   for( i = 0 ; i < length; i++) { coord.row fixed already        for( i = 0 ; i < length; i++) { coord.row fixed already
377   *     coord.col = a[i++];          coord.col = a[i++];
378   *     mtx_fill_org_value(mtx,&coord,d[a[i]])          mtx_fill_org_value(mtx,&coord,d[a[i]])
379   *   }        }
380   * }      }
381   *  
382   * One begins to wonder if there isn't a better way to do all this, but      One begins to wonder if there isn't a better way to do all this, but
383   * so far nothing has occurred.      so far nothing has occurred.
384   * The best way would be to feed clients only the block of stuff they      The best way would be to feed clients only the block of stuff they
385   * are interested in (no fixed, unattached vars or unincluded rels      are interested in (no fixed, unattached vars or unincluded rels
386   * or vars/rels solved in previous partitions) so that the solver      or vars/rels solved in previous partitions) so that the solver
387   * had no partitioning or var classification work to do except perhaps      had no partitioning or var classification work to do except perhaps
388   * classifying things as basic/nonbasic.      classifying things as basic/nonbasic.
389   */  */
390    
   
391  /* return a pointer to the oncesizefitsall ips we're using.  /* return a pointer to the oncesizefitsall ips we're using.
392   * always returns nonnull because if we run out we exit      always returns nonnull because if we run out we exit
393   */  */
394  static struct solver_ipdata *analyze_getip(void)  static struct solver_ipdata *analyze_getip(void)
395  {  {
396    if (g_reuse.ipbuf!=NULL && g_reuse.ipused < g_reuse.ipcap) {    if (g_reuse.ipbuf!=NULL && g_reuse.ipused < g_reuse.ipcap) {
# Line 404  static struct solver_ipdata *analyze_get Line 403  static struct solver_ipdata *analyze_get
403  }  }
404    
405  /*  /*
406   * reallocates to the requested size (newcap) the ipbuf.      reallocates to the requested size (newcap) the ipbuf.
407   * if newcap = 0, frees ipbuf.      if newcap = 0, frees ipbuf.
408   * if insufficient memory returns 1.      if insufficient memory returns 1.
409   * if newcap > 0 and reset mem != 0, initializes ipbuf to 0s.      if newcap > 0 and reset mem != 0, initializes ipbuf to 0s.
410   * Resets ipused to 0.      Resets ipused to 0.
411   */  */
412  static  static
413  int resize_ipbuf(size_t newcap, int resetmem)  int resize_ipbuf(size_t newcap, int resetmem)
414  {  {
# Line 454  int resize_ipbuf(size_t newcap, int rese Line 453  int resize_ipbuf(size_t newcap, int rese
453    
454    
455  /*  /*
456   * checks size of request and returns a pointer to the next available      checks size of request and returns a pointer to the next available
457   * chunk of incidence space. if too much requested or 0 requested returns      chunk of incidence space. if too much requested or 0 requested returns
458   * NULL. p_data->relincidence must have been allocated for this to work.      NULL. p_data->relincidence must have been allocated for this to work.
459   */  */
460  static  static
461  struct var_variable **get_incidence_space(int len, struct problem_t *p_data)  struct var_variable **get_incidence_space(int len, struct problem_t *p_data)
462  {  {
# Line 476  struct var_variable **get_incidence_spac Line 475  struct var_variable **get_incidence_spac
475  }  }
476    
477  /*  /*
478   * checks size of request and returns a pointer to the next available      checks size of request and returns a pointer to the next available
479   * chunk of incidence space. if too much requested or 0 requested returns      chunk of incidence space. if too much requested or 0 requested returns
480   * NULL. p_data->varincidence must have been allocated for this to work.      NULL. p_data->varincidence must have been allocated for this to work.
481   */  */
482  static  static
483  struct rel_relation **get_var_incidence_space(int len,  struct rel_relation **get_var_incidence_space(int len,
484                                                struct problem_t *p_data)                                                struct problem_t *p_data)
# Line 500  struct rel_relation **get_var_incidence_ Line 499  struct rel_relation **get_var_incidence_
499    
500    
501  /*  /*
502   * p_data->logrelinciden must have been allocated for this to work.      p_data->logrelinciden must have been allocated for this to work.
503   */  */
504  static  static
505  struct dis_discrete **get_logincidence_space(int len,  struct dis_discrete **get_logincidence_space(int len,
506                                               struct problem_t *p_data)                                               struct problem_t *p_data)
# Line 522  struct dis_discrete **get_logincidence_s Line 521  struct dis_discrete **get_logincidence_s
521    
522    
523  /*  /*
524   * InitTreeCounts(i); This resets the pointers and counters in      InitTreeCounts(i); This resets the pointers and counters in
525   * p_data to null. p_data is supposed to be a temporary structure      p_data to null. p_data is supposed to be a temporary structure
526   * so the memory management of the pointers in p_data is the job      so the memory management of the pointers in p_data is the job
527   * of the caller.      of the caller.
528   * p_data->root is set to i.      p_data->root is set to i.
529   */  */
530  static void InitTreeCounts(struct Instance *i,struct problem_t *p_data)  static void InitTreeCounts(struct Instance *i,struct problem_t *p_data)
531  {  {
532    memset((char *)p_data,0,sizeof(struct problem_t));    memset((char *)p_data,0,sizeof(struct problem_t));
# Line 541  static void InitTreeCounts(struct Instan Line 540  static void InitTreeCounts(struct Instan
540  #define PART_THRESHOLD 1000  #define PART_THRESHOLD 1000
541    
542  /*  /*
543   * The following function should be moved out to the compiler      The following function should be moved out to the compiler
544   * under the guise of a supported attribute.      under the guise of a supported attribute.
545   */  */
546  static int BooleanChildValue(struct Instance *i,symchar *sc)  static int BooleanChildValue(struct Instance *i,symchar *sc)
547  {  {
548    /* FPRINTF(ASCERR,"GETTING BOOLEAN CHILD VALUE OF %s\n",SCP(sc)); */    /* FPRINTF(ASCERR,"GETTING BOOLEAN CHILD VALUE OF %s\n",SCP(sc)); */
# Line 625  static void CollectArrayRelsAndWhens(str Line 624  static void CollectArrayRelsAndWhens(str
624    
625    
626  /*  /*
627   * Collect all the logrels/relations at the local scope of the MODEL      Collect all the logrels/relations at the local scope of the MODEL
628   * associated with ip->i. Local scope includes arrays of logrels/relations,      associated with ip->i. Local scope includes arrays of logrels/relations,
629   * mainly because these arrays don't have interface pointers so we      mainly because these arrays don't have interface pointers so we
630   * can't treat them separately.      can't treat them separately.
631   */  */
632  static void CollectRelsAndWhens(struct solver_ipdata *ip,  static void CollectRelsAndWhens(struct solver_ipdata *ip,
633                                  long modindex,                                  long modindex,
634                                  struct problem_t *p_data)                                  struct problem_t *p_data)
# Line 687  static void CollectRelsAndWhens(struct s Line 686  static void CollectRelsAndWhens(struct s
686    }    }
687  }  }
688    
   
   
689  /*  /*
690   * Checks the problem extrels list to see whether a cache has been      Checks the problem extrels list to see whether a cache has been
691   * created for the given relation in the problem_t bridge.      created for the given relation in the problem_t bridge.
692   * If not will return NULL, else      If not will return NULL, else
693   * will return the pointer to the cache. The nodestamp corresponding      will return the pointer to the cache. The nodestamp corresponding
694   * to this relation is returned regardless.      to this relation is returned regardless.
695   *  */
  */  
696  static struct ExtRelCache  static struct ExtRelCache
697    *CheckIfCacheExists( struct Instance *relinst, int *nodestamp,    *CheckIfCacheExists( struct Instance *relinst, int *nodestamp,
698                         struct problem_t *p_data)                         struct problem_t *p_data)
# Line 721  static struct ExtRelCache Line 717  static struct ExtRelCache
717    }    }
718    return NULL;    return NULL;
719  }  }
720    
721  /*  /*
722   * analyze_CountRelation      analyze_CountRelation
723   * Call only with good relation instances.      Call only with good relation instances.
724   * Count the instance into the required bin.      Count the instance into the required bin.
725   */  */
726  static void analyze_CountRelation(struct Instance *inst,  static void analyze_CountRelation(struct Instance *inst,
727                                    struct problem_t *p_data)                                    struct problem_t *p_data)
728  {  {
# Line 753  static void analyze_CountRelation(struct Line 749  static void analyze_CountRelation(struct
749      FPRINTF(ASCERR,"        Unknown relation type.\n");      FPRINTF(ASCERR,"        Unknown relation type.\n");
750    }    }
751  }  }
752    
753    
754  /*  /*
755   * GetIntFromSymbol      GetIntFromSymbol
756   * Used for a WHEN statement. It intends to obtain an integer value      Used for a WHEN statement. It intends to obtain an integer value
757   * from a symbol value. Each symbol value is storaged in a symbol list.      from a symbol value. Each symbol value is storaged in a symbol list.
758   * It checks if the symval is already in the solver symbol list,      It checks if the symval is already in the solver symbol list,
759   * if it is, returns the integer corresponding to the position of symval      if it is, returns the integer corresponding to the position of symval
760   * if it is not, appends the symval to the list and then returns the int      if it is not, appends the symval to the list and then returns the int
761   * This is terrible inefficient as the number of symbols grows.      This is terrible inefficient as the number of symbols grows.
762   * I am keeping it by now, are they going to be so many symbols in      I am keeping it by now, are they going to be so many symbols in
763   * whens anyway ?      whens anyway ?
764   */  */
765    
766  int GetIntFromSymbol(CONST char *symval,  int GetIntFromSymbol(CONST char *symval,
767               struct gl_list_t *symbol_list)               struct gl_list_t *symbol_list)
# Line 817  void DestroySymbolValuesList(struct gl_l Line 813  void DestroySymbolValuesList(struct gl_l
813  }  }
814    
815    
   
   
816  /*  /*
817   * classify_instance : to be called by PushInterfacPtrs.      classify_instance : to be called by PushInterfacPtrs.
818   *  
819   * This function classifies the given instance and appends into      This function classifies the given instance and appends into
820   * the necessary list in the p_data structure.      the necessary list in the p_data structure.
821   * It also sets returns a pointer to the caller for insertion into      It also sets returns a pointer to the caller for insertion into
822   * the interface_ptr slot.      the interface_ptr slot.
823   *  
824   * Note, we should be passing the ipbuf info via vp so we don't      Note, we should be passing the ipbuf info via vp so we don't
825   * need the nasty global variable and can be more thread safe.      need the nasty global variable and can be more thread safe.
826   * vp is a struct problem_t.      vp is a struct problem_t.
827   */  */
828  static  static
829  void *classify_instance(struct Instance *inst, VOIDPTR vp)  void *classify_instance(struct Instance *inst, VOIDPTR vp)
830  {  {
# Line 1071  void *classify_instance(struct Instance Line 1065  void *classify_instance(struct Instance
1065      return NULL;      return NULL;
1066    }    }
1067  }  }
1068    
 /*  
  * make_problem  
  *  
  *  Makes variable/relations/when lists and objective function by heuristic.  
  *  Now also makes a list of all relations that are objectives.  
  *  This does not affect the semantics of the previous objective  
  *  code.  
  *  Do NOTHING in this function which can lead to floating point  
  *  errors -- in particular because we must leave the interface ptrs  
  *  in the state they were found.  
  */  
1069  /*  /*
1070   * This function sets g_bad_rel_in_list TRUE if it finds any unhappy      make_problem
1071   * relations. All the rest of the code depends on ALL relations being  
1072   * good, so don't disable the g_bad_rel_in_list feature.      Makes variable/relations/when lists and objective function by heuristic.
1073   */      Now also makes a list of all relations that are objectives.
1074        This does not affect the semantics of the previous objective
1075        code.
1076        Do NOTHING in this function which can lead to floating point
1077        errors -- in particular because we must leave the interface ptrs
1078        in the state they were found.
1079    */
1080    /*
1081        This function sets g_bad_rel_in_list TRUE if it finds any unhappy
1082        relations. All the rest of the code depends on ALL relations being
1083        good, so don't disable the g_bad_rel_in_list feature.
1084    */
1085  static  static
1086  void CountStuffInTree(struct Instance *inst, struct problem_t *p_data)  void CountStuffInTree(struct Instance *inst, struct problem_t *p_data)
1087  {  {
# Line 1121  void CountStuffInTree(struct Instance *i Line 1115  void CountStuffInTree(struct Instance *i
1115          }          }
1116        }        }
1117        /* The use of  RelationsCount is heuristic since vars may be        /* The use of  RelationsCount is heuristic since vars may be
1118         * used in relations higher in the tree than the problem is rooted.          used in relations higher in the tree than the problem is rooted.
1119         */         */
1120        break;        break;
1121      case BOOLEAN_ATOM_INST:      case BOOLEAN_ATOM_INST:
# Line 1181  void CountStuffInTree(struct Instance *i Line 1175  void CountStuffInTree(struct Instance *i
1175    }    }
1176  }  }
1177    
1178    
1179  /*  /*
1180   * This takes the already derived counts,      This takes the already derived counts,
1181   * allocates all the memory we need to allocate for master,      allocates all the memory we need to allocate for master,
1182   * and builds the var/rel/MODEL/etc master lists.      and builds the var/rel/MODEL/etc master lists.
1183   * filling in p_data and ips as far as possible.      filling in p_data and ips as far as possible.
1184   * Returns 0 normally, or 1 if insufficient memory, 2 if nothing to do.      Returns 0 normally, or 1 if insufficient memory, 2 if nothing to do.
1185   * If 1, then the user should deallocate any partial results in      If 1, then the user should deallocate any partial results in
1186   * a separate cleanup function for p_data->      a separate cleanup function for p_data->
1187   *  
1188   * In particular, after this is done we have      In particular, after this is done we have
1189   * vars with correct ip values for:      vars with correct ip values for:
1190   * index;      index;
1191   *  incident;       incident;
1192   *  in_block;       in_block;
1193   *  fixed;  (as flag)       fixed; (as flag)
1194   *  basis;      (as flag)       basis;      (as flag)
1195   *  solvervar;  (as flag)       solvervar; (as flag)
1196   * relations and conditional relations with correct ip values for:      relations and conditional relations with correct ip values for:
1197   *  index;       index;
1198   *  model;       model;
1199   *  obj;        (0 constraint, -1 maximize, +1 minimize)       obj;       (0 constraint, -1 maximize, +1 minimize)
1200   *  ext;       ext;
1201   *  inwhen;       inwhen;
1202   *  cond;       cond;
1203   *  included;   (as flag)       included;  (as flag)
1204   * discrete vars with correct ip values for:      discrete vars with correct ip values for:
1205   *  index;       index;
1206   *  incident;       incident;
1207   *  isconst;       isconst;
1208   *  distype;       distype;
1209   *  fixed;  (as flag)       fixed; (as flag)
1210   *  booleanvar; (as flag)       booleanvar;    (as flag)
1211   *  inwhen;       inwhen;
1212   * logrelations and conditional logrelations with correct ip values for:      logrelations and conditional logrelations with correct ip values for:
1213   *  index;       index;
1214   *  model;       model;
1215   *  included;   (as flag)       included;  (as flag)
1216   *  inwhen;       inwhen;
1217   *  cond;       cond;
1218   * whens with correct ip values for:      whens with correct ip values for:
1219   *  index;       index;
1220   *  model;       model;
1221   *  inwhen;       inwhen;
1222   * models with correct ip values for:      models with correct ip values for:
1223   *  index;       index;
1224   *  
1225   * Note that these are all indexed from 1, being stored in gllists.      Note that these are all indexed from 1, being stored in gllists.
1226   */  */
1227  static int analyze_make_master_lists(struct problem_t *p_data)  static int analyze_make_master_lists(struct problem_t *p_data)
1228  {  {
1229    long int c, len,v,vlen;    long int c, len,v,vlen;
# Line 1309  static int analyze_make_master_lists(str Line 1303  static int analyze_make_master_lists(str
1303    }    }
1304    
1305    /*    /*
1306     * collect relations, objectives, logrels and whens recording the      collect relations, objectives, logrels and whens recording the
1307     * MODEL number in each rel's ip and setting incidence.      MODEL number in each rel's ip and setting incidence.
1308     */    */
1309    len = gl_length(p_data->models);    len = gl_length(p_data->models);
1310    for (c=1; c <= len; c++) {    for (c=1; c <= len; c++) {
1311      CollectRelsAndWhens(SIP(gl_fetch(p_data->models,c)),c,p_data);      CollectRelsAndWhens(SIP(gl_fetch(p_data->models,c)),c,p_data);
# Line 1333  static int analyze_make_master_lists(str Line 1327  static int analyze_make_master_lists(str
1327        gl_length(p_data->whens), p_data->nw);        gl_length(p_data->whens), p_data->nw);
1328    }    }
1329    /*    /*
1330     * relation list is now grouped by model, and the order will be      relation list is now grouped by model, and the order will be
1331     * invariant with hardware and ascend invocation so long as      invariant with hardware and ascend invocation so long as
1332     * set FIRSTCHOICE holds in compilation.      set FIRSTCHOICE holds in compilation.
1333     */    */
1334    /* mark vars in constraints incident  and index rels */    /* mark vars in constraints incident  and index rels */
1335    len = gl_length(p_data->rels);    len = gl_length(p_data->rels);
1336    for (c=1; c <= len; c++) {    for (c=1; c <= len; c++) {
# Line 1402  static int analyze_make_master_lists(str Line 1396  static int analyze_make_master_lists(str
1396      SIP(gl_fetch(p_data->whens,c))->u.w.index = c;      SIP(gl_fetch(p_data->whens,c))->u.w.index = c;
1397    }    }
1398    /*    /*
1399     * now we need to move all the nonincident vars off the var list      now we need to move all the nonincident vars off the var list
1400     * onto the unas list. It is easiest to make a new list and copy      onto the unas list. It is easiest to make a new list and copy
1401     * the existing var list to either it if keep or unas if punt.      the existing var list to either it if keep or unas if punt.
1402     * the same goes for parameters that aren't incident.      the same goes for parameters that aren't incident.
1403     * We don't do exactly the same for discrete variables because      We don't do exactly the same for discrete variables because
1404     * many of them are not incident but they are used in when's      many of them are not incident but they are used in when's
1405     */    */
1406    len = gl_length(p_data->vars);    len = gl_length(p_data->vars);
1407    p_data->tmplist = gl_create(len);    p_data->tmplist = gl_create(len);
1408    if (p_data->tmplist == NULL) return 1;    if (p_data->tmplist == NULL) return 1;
# Line 1449  static int analyze_make_master_lists(str Line 1443  static int analyze_make_master_lists(str
1443    p_data->nu = gl_length(p_data->unas);    p_data->nu = gl_length(p_data->unas);
1444    
1445    /*    /*
1446     * discrete variables: take the incident dis vars in logrels first,      discrete variables: take the incident dis vars in logrels first,
1447     * then append the dis vars which are used only in whens      then append the dis vars which are used only in whens
1448     */    */
1449    p_data->lrelinc = 0;    p_data->lrelinc = 0;
1450    len = gl_length(p_data->dvars);    len = gl_length(p_data->dvars);
1451    if ( len > 0) {    if ( len > 0) {
# Line 1482  static int analyze_make_master_lists(str Line 1476  static int analyze_make_master_lists(str
1476    }    }
1477    
1478    /*    /*
1479     * The following patch is to avoid the system to crash.      The following patch is to avoid the system to crash.
1480     * When multiple definitions of a solver_var have introduced into the      When multiple definitions of a solver_var have introduced into the
1481     * system, ASCEND may fail in identifying that a REAL_ATOM is a refinement      system, ASCEND may fail in identifying that a REAL_ATOM is a refinement
1482     * of a solver_var. This causes the system to think that, even that there      of a solver_var. This causes the system to think that, even that there
1483     * are relations into the system, there are no incidences in these relations      are relations into the system, there are no incidences in these relations
1484     * that fall into the category of a variable. As a consequence, the length      that fall into the category of a variable. As a consequence, the length
1485     * of the list of variables is zero. That of course will introduce      of the list of variables is zero. That of course will introduce
1486     * insanities while trying to build the slv system. Some      insanities while trying to build the slv system. Some
1487     * solutions to this problem are:      solutions to this problem are:
1488     *  
1489     * The easier for us is just to alert the user and to force him/her to      The easier for us is just to alert the user and to force him/her to
1490     * reload all the type defintions again. That is the current solution      reload all the type defintions again. That is the current solution
1491     *  
1492     * The correct (but time consuming) solution is the implementation of a      The correct (but time consuming) solution is the implementation of a
1493     * SolverAtomInstance, which still needs parser and interpreter support      SolverAtomInstance, which still needs parser and interpreter support
1494     *    */
    */  
1495    
1496    if (p_data->nr != 0 &&  p_data->nv==0) {    if (p_data->nr != 0 &&  p_data->nv==0) {
1497      FPRINTF(ASCERR, "\n");      FPRINTF(ASCERR, "\n");
# Line 1525  static int analyze_make_master_lists(str Line 1518  static int analyze_make_master_lists(str
1518    
1519    
1520  /*  /*
1521   *  This function cleans up an errant problem_t or a good one that we're       This function cleans up an errant problem_t or a good one that we're
1522   *  done with. We should have set to null any pointers to memory we are       done with. We should have set to null any pointers to memory we are
1523   *  keeping elsewhere before calling this.       keeping elsewhere before calling this.
1524   */  */
1525  #define AFUN(ptr) if (ptr!=NULL) ascfree(ptr); (ptr) = NULL  #define AFUN(ptr) if (ptr!=NULL) ascfree(ptr); (ptr) = NULL
1526  #define ADUN(ptr) if (ptr!=NULL) gl_destroy(ptr); (ptr) = NULL  #define ADUN(ptr) if (ptr!=NULL) gl_destroy(ptr); (ptr) = NULL
1527  static void analyze_free_lists(struct problem_t *p_data)  static void analyze_free_lists(struct problem_t *p_data)
# Line 1595  static void analyze_free_lists(struct pr Line 1588  static void analyze_free_lists(struct pr
1588    
1589    
1590  /*  /*
1591   *                           When Processing                                'WHEN' Processing
1592   */  */
1593    
1594  /*  /*
1595   * This function receives as argument the list of values of each of the      This function receives as argument the list of values of each of the
1596   * CASES of a WHEN statement. The values in the list can be integer values,      CASES of a WHEN statement. The values in the list can be integer values,
1597   * symbol values, or boolean values. So, the goal of this function is to      symbol values, or boolean values. So, the goal of this function is to
1598   * obtain an equivalent list of ONLY integer values for such a list. In this      obtain an equivalent list of ONLY integer values for such a list. In this
1599   * way, for example, the boolean value TRUE is equivalent to the integer      way, for example, the boolean value TRUE is equivalent to the integer
1600   * 1. The function GentIntFromSymbol is used to generate an integer value      1. The function GentIntFromSymbol is used to generate an integer value
1601   * which will be equivalent to a symbol value      which will be equivalent to a symbol value
1602   */  */
1603  static  static
1604  void ProcessValueList(struct Set *ValueList, int *value,  void ProcessValueList(struct Set *ValueList, int *value,
1605                struct gl_list_t *symbol_list)                struct gl_list_t *symbol_list)
# Line 1644  void ProcessValueList(struct Set *ValueL Line 1637  void ProcessValueList(struct Set *ValueL
1637    
1638    
1639  /*  /*
1640   * The next two functions are used because in the function      The next two functions are used because in the function
1641   * ProcessSolverWhens, the existence of MODELS or ARRAYs inside      ProcessSolverWhens, the existence of MODELS or ARRAYs inside
1642   * a When Statement requires a recursive analysis.      a When Statement requires a recursive analysis.
1643   * See the explanation of such a function      See the explanation of such a function
1644   */  */
1645  static  static
1646  void ProcessArraysInWhens(struct Instance *cur_inst,  void ProcessArraysInWhens(struct Instance *cur_inst,
1647                struct gl_list_t *rels,                struct gl_list_t *rels,
# Line 1755  void ProcessModelsInWhens(struct Instanc Line 1748  void ProcessModelsInWhens(struct Instanc
1748    
1749    
1750  /*  /*
1751   * The goal of this function is to fill in the list of cases and variables      The goal of this function is to fill in the list of cases and variables
1752   * of a w_when structure with the appropriate data. The information required      of a w_when structure with the appropriate data. The information required
1753   * is provided by the corresponding when Instance generated in the      is provided by the corresponding when Instance generated in the
1754   * compilation time. So, what we do is:      compilation time. So, what we do is:
1755   * 1) Obtain the list of variables and the list of cases from each      1) Obtain the list of variables and the list of cases from each
1756   *    WHEN intance.         WHEN intance.
1757   *    The list of variables is actually a list of pointers to instances         The list of variables is actually a list of pointers to instances
1758   * 2) From each CASE, obtain also the list of references. This list of      2) From each CASE, obtain also the list of references. This list of
1759   * references contains a list of pointers to each relation,logrelation  and      references contains a list of pointers to each relation,logrelation  and
1760   * model included inside the case.      model included inside the case.
1761   * 3) The pointers to the variables, relations, logrelations and models are      3) The pointers to the variables, relations, logrelations and models are
1762   * used to obtain the solver data associated with the compiled instances.      used to obtain the solver data associated with the compiled instances.
1763   * 4) Arrays and models are managed recursively with the two previous      4) Arrays and models are managed recursively with the two previous
1764   * functions.      functions.
1765   */  */
1766  static  static
1767  void ProcessSolverWhens(struct w_when *when,struct Instance *i)  void ProcessSolverWhens(struct w_when *when,struct Instance *i)
1768  {  {
# Line 1865  void ProcessSolverWhens(struct w_when *w Line 1858  void ProcessSolverWhens(struct w_when *w
1858    
1859    
1860  /*  /*
1861   * Next two functions are for needed in the reconfiguration of      Next two functions are for needed in the reconfiguration of
1862   * conditional models      conditional models
1863   */  */
1864    
1865  /*  /*
1866   * return 1 if the discrete var is a member of the when var list, else      return 1 if the discrete var is a member of the when var list, else
1867   * return 0      return 0
1868   */  */
1869  int dis_var_in_a_when(struct Instance *var, struct w_when *when)  int dis_var_in_a_when(struct Instance *var, struct w_when *when)
1870  {  {
1871    struct Instance *winst;    struct Instance *winst;
# Line 1883  int dis_var_in_a_when(struct Instance *v Line 1876  int dis_var_in_a_when(struct Instance *v
1876    
1877    
1878  /*  /*
1879   * Determine if the conditional variable inst is part of the      Determine if the conditional variable inst is part of the
1880   * variable list of some when in the when list.      variable list of some when in the when list.
1881   */  */
1882  int varinst_found_in_whenlist(slv_system_t sys, struct Instance *inst)  int varinst_found_in_whenlist(slv_system_t sys, struct Instance *inst)
1883  {  {
1884    struct w_when **whenlist;    struct w_when **whenlist;
# Line 1902  int varinst_found_in_whenlist(slv_system Line 1895  int varinst_found_in_whenlist(slv_system
1895    return 0;    return 0;
1896  }  }
1897    
1898    
1899    
1900  /*  /*
1901   *                           Boundary Processing                                Boundary Processing
1902   */  */
1903    
1904  /*  /*
1905   * Get the list or logrelation including a boundary (by means of a      Get the list or logrelation including a boundary (by means of a
1906   * SATISFIED term). This function look the structures in the compiler      SATISFIED term). This function look the structures in the compiler
1907   * side and make the same link in the solver side      side and make the same link in the solver side
1908   */  */
1909  static  static
1910  void GetListOfLogRels(struct bnd_boundary *bnd, struct Instance *inst)  void GetListOfLogRels(struct bnd_boundary *bnd, struct Instance *inst)
1911  {  {
# Line 1938  void GetListOfLogRels(struct bnd_boundar Line 1931  void GetListOfLogRels(struct bnd_boundar
1931  }  }
1932    
1933  /*  /*
1934   * Get the tolerance used to define the satisfaction of a boundary      Get the tolerance used to define the satisfaction of a boundary
1935   * (Defined in the SATISFIED term)      (Defined in the SATISFIED term)
1936   */  */
1937  static  static
1938  void GetTolerance(struct bnd_boundary *bnd)  void GetTolerance(struct bnd_boundary *bnd)
1939  {  {
# Line 1964  void GetTolerance(struct bnd_boundary *b Line 1957  void GetTolerance(struct bnd_boundary *b
1957  }  }
1958    
1959    
1960    
1961    
1962  /*  /*
1963   * Here we roll the master lists and bridge data into relation/var/      Here we roll the master lists and bridge data into relation/var/
1964   * logrelation/conditional/when etc. lists for the consumer.      logrelation/conditional/when etc. lists for the consumer.
1965   * Includes fixing up rel caches and initing flagbits as best we can.      Includes fixing up rel caches and initing flagbits as best we can.
1966   * includes setting master indices on rel/var/logrel/when etc.      includes setting master indices on rel/var/logrel/when etc.
1967   * returns 0 if ok, 1 if out of memory, 2 if the problem does not      returns 0 if ok, 1 if out of memory, 2 if the problem does not
1968   * contain at least one variable in one equation      contain at least one variable in one equation
1969   */  */
1970  static int analyze_make_solvers_lists(struct problem_t *p_data)  static int analyze_make_solvers_lists(struct problem_t *p_data)
1971  {  {
1972    CONST struct relation *gut;    CONST struct relation *gut;
# Line 2042  static int analyze_make_solvers_lists(st Line 2035  static int analyze_make_solvers_lists(st
2035    
2036    
2037    /*    /*
2038     * calculate the number of free and incident variables, ncol      calculate the number of free and incident variables, ncol
2039     * we put all the nonincident on the unas list, so just check fixed.      we put all the nonincident on the unas list, so just check fixed.
2040     */    */
2041    for (c=1,len = gl_length(p_data->vars); c <= len; c++) {    for (c=1,len = gl_length(p_data->vars); c <= len; c++) {
2042      vip = SIP(gl_fetch(p_data->vars,c));      vip = SIP(gl_fetch(p_data->vars,c));
2043      if (!(vip->u.v.fixed)) p_data->ncol++;      if (!(vip->u.v.fixed)) p_data->ncol++;
2044    }    }
2045    /*    /*
2046     * now, at last we have cols jacobian in the order we want the lists to      now, at last we have cols jacobian in the order we want the lists to
2047     * be handed to the solvers.      be handed to the solvers.
2048     */    */
2049    
2050    
2051    logorder = MAX((unsigned long)p_data->lrelinc,gl_length(p_data->logrels));    logorder = MAX((unsigned long)p_data->lrelinc,gl_length(p_data->logrels));
2052    lognnzold = p_data->lognnz = p_data->lrelincsize = 0;    lognnzold = p_data->lognnz = p_data->lrelincsize = 0;
# Line 2095  static int analyze_make_solvers_lists(st Line 2088  static int analyze_make_solvers_lists(st
2088      return 2;      return 2;
2089    }    }
2090    /*    /*
2091     * we want at least one variable in one obj or rel,      we want at least one variable in one obj or rel,
2092     * or at least one boolean variable in one logrel      or at least one boolean variable in one logrel
2093     */    */
2094    
2095    
2096    /* calculate the number of free and incident boolean variables, logncol */    /* calculate the number of free and incident boolean variables, logncol */
# Line 2105  static int analyze_make_solvers_lists(st Line 2098  static int analyze_make_solvers_lists(st
2098      dvip = SIP(gl_fetch(p_data->dvars,c));      dvip = SIP(gl_fetch(p_data->dvars,c));
2099      if (!(dvip->u.dv.fixed)) p_data->logncol++;      if (!(dvip->u.dv.fixed)) p_data->logncol++;
2100    }    }
2101    
2102    
2103    /* now malloc and build things, remember to punt the matrix soon */    /* now malloc and build things, remember to punt the matrix soon */
2104    /* remember we must NEVER free these things individually. */    /* remember we must NEVER free these things individually. */
# Line 2221  static int analyze_make_solvers_lists(st Line 2214  static int analyze_make_solvers_lists(st
2214    p_data->lrelincinuse = 0;    p_data->lrelincinuse = 0;
2215    
2216    /*    /*
2217     * for c in varlist copy vardata. remember gllist # from 1 and data from 0      for c in varlist copy vardata. remember gllist # from 1 and data from 0
2218     */    */
2219    /*    /*
2220     * for c in varlist set mastervl, solvervl pointer to point to data      for c in varlist set mastervl, solvervl pointer to point to data
2221     */    */
2222    vlen = gl_length(p_data->vars);    vlen = gl_length(p_data->vars);
2223    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2224      var = &(p_data->vardata[v]);      var = &(p_data->vardata[v]);
# Line 2248  static int analyze_make_solvers_lists(st Line 2241  static int analyze_make_solvers_lists(st
2241    p_data->mastervl[vlen] = NULL; /* terminator */    p_data->mastervl[vlen] = NULL; /* terminator */
2242    p_data->solvervl[vlen] = NULL; /* terminator */    p_data->solvervl[vlen] = NULL; /* terminator */
2243    /*    /*
2244     * for c in parlist copy pardata. remember gllist # from 1 and data from 0      for c in parlist copy pardata. remember gllist # from 1 and data from 0
2245     * for c in parlist set masterpl, solverpl pointer to point to data      for c in parlist set masterpl, solverpl pointer to point to data
2246     */    */
2247    vlen = gl_length(p_data->pars);    vlen = gl_length(p_data->pars);
2248    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2249      var = &(p_data->pardata[v]);      var = &(p_data->pardata[v]);
# Line 2272  static int analyze_make_solvers_lists(st Line 2265  static int analyze_make_solvers_lists(st
2265    p_data->masterpl[vlen] = NULL; /* terminator */    p_data->masterpl[vlen] = NULL; /* terminator */
2266    p_data->solverpl[vlen] = NULL; /* terminator */    p_data->solverpl[vlen] = NULL; /* terminator */
2267    /*    /*
2268     * for c in unalist copy undata. remember gllist # from 1 and data from 0      for c in unalist copy undata. remember gllist # from 1 and data from 0
2269     * for c in unalist set masterul, solverul pointer to point to data      for c in unalist set masterul, solverul pointer to point to data
2270     */    */
2271    vlen = gl_length(p_data->unas);    vlen = gl_length(p_data->unas);
2272    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2273      var = &(p_data->undata[v]);      var = &(p_data->undata[v]);
# Line 2295  static int analyze_make_solvers_lists(st Line 2288  static int analyze_make_solvers_lists(st
2288    }    }
2289    p_data->masterul[vlen] = NULL; /* terminator */    p_data->masterul[vlen] = NULL; /* terminator */
2290    p_data->solverul[vlen] = NULL; /* terminator */    p_data->solverul[vlen] = NULL; /* terminator */
2291    
2292    /*    /*
2293     * process the constraining relations      process the constraining relations
2294     * for v in rellist copy reldata and fix extrels.      for v in rellist copy reldata and fix extrels.
2295     */    */
2296    vlen = gl_length(p_data->rels);    vlen = gl_length(p_data->rels);
2297    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2298      rel = &(p_data->reldata[v]);      rel = &(p_data->reldata[v]);
# Line 2359  static int analyze_make_solvers_lists(st Line 2352  static int analyze_make_solvers_lists(st
2352      p_data->erlist[c-1] = (struct ExtRelCache *)gl_fetch(p_data->extrels,c);      p_data->erlist[c-1] = (struct ExtRelCache *)gl_fetch(p_data->extrels,c);
2353    }    }
2354    p_data->erlist[len] = NULL; /* terminator */    p_data->erlist[len] = NULL; /* terminator */
2355    
2356  /*  /*
2357   * for c in objlist copy objdata.      for c in objlist copy objdata.
2358   * for c in objlist set masterrl, solverrl pointer to point to data.      for c in objlist set masterrl, solverrl pointer to point to data.
2359   */  */
2360    /*    /*
2361     * process the objective relations      process the objective relations
2362     * for v in objlist copy objdata      for v in objlist copy objdata
2363     */    */
2364    vlen = gl_length(p_data->objrels);    vlen = gl_length(p_data->objrels);
2365    found = 0;    found = 0;
2366    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
# Line 2413  static int analyze_make_solvers_lists(st Line 2406  static int analyze_make_solvers_lists(st
2406    p_data->solverol[vlen] = NULL; /* terminator */    p_data->solverol[vlen] = NULL; /* terminator */
2407    
2408    /*    /*
2409     * process the conditional relations      process the conditional relations
2410     * for v in cndlist copy conddata .      for v in cndlist copy conddata .
2411     */    */
2412    vlen = gl_length(p_data->cnds);    vlen = gl_length(p_data->cnds);
2413    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2414      rel = &(p_data->condata[v]);      rel = &(p_data->condata[v]);
# Line 2458  static int analyze_make_solvers_lists(st Line 2451  static int analyze_make_solvers_lists(st
2451    
2452    
2453    /*    /*
2454     * process discrete variables      process discrete variables
2455     * for c in dvarlist copy disdata. gllist # from 1 and data from 0      for c in dvarlist copy disdata. gllist # from 1 and data from 0
2456     * for c in dvarlist set masterdl, solverdl pointer to point to data      for c in dvarlist set masterdl, solverdl pointer to point to data
2457     */    */
2458    vlen = gl_length(p_data->dvars);    vlen = gl_length(p_data->dvars);
2459    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2460      dvar = &(p_data->disdata[v]);      dvar = &(p_data->disdata[v]);
2461      dvip = SIP(gl_fetch(p_data->dvars,v+1));      dvip = SIP(gl_fetch(p_data->dvars,v+1));
2462      /*      /*
2463      dvip->u.dv.data = dvar;        dvip->u.dv.data = dvar;
2464      dis_set_instance(dvar,dvip->i); */        dis_set_instance(dvar,dvip->i); */
2465      /* from here */      /* from here */
2466      dis_create(dvip->i,dvar);      dis_create(dvip->i,dvar);
2467      dvip->u.dv.data = dvar;      dvip->u.dv.data = dvar;
# Line 2507  static int analyze_make_solvers_lists(st Line 2500  static int analyze_make_solvers_lists(st
2500    p_data->solverdl[vlen] = NULL; /* terminator */    p_data->solverdl[vlen] = NULL; /* terminator */
2501    
2502    /*    /*
2503     * for c in dunalist copy undisdata. gllist # from 1 and data from 0      for c in dunalist copy undisdata. gllist # from 1 and data from 0
2504     * for c in dunalist set masterdul, solverdul pointer to point to data      for c in dunalist set masterdul, solverdul pointer to point to data
2505     */    */
2506    vlen = gl_length(p_data->dunas);    vlen = gl_length(p_data->dunas);
2507    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2508      dvar = &(p_data->undisdata[v]);      dvar = &(p_data->undisdata[v]);
# Line 2528  static int analyze_make_solvers_lists(st Line 2521  static int analyze_make_solvers_lists(st
2521    }    }
2522    p_data->masterdul[vlen] = NULL; /* terminator */    p_data->masterdul[vlen] = NULL; /* terminator */
2523    p_data->solverdul[vlen] = NULL; /* terminator */    p_data->solverdul[vlen] = NULL; /* terminator */
2524    
2525    
2526  /*  /*
2527   * for c in logrellist copy lrdata.      for c in logrellist copy lrdata.
2528   * for c in logrellist set masterll, solverll pointer to point to data.      for c in logrellist set masterll, solverll pointer to point to data.
2529   */  */
2530    /*    /*
2531     * process the logical relations      process the logical relations
2532     * for v in logrellist copy lrdata      for v in logrellist copy lrdata
2533     */    */
2534    vlen = gl_length(p_data->logrels);    vlen = gl_length(p_data->logrels);
2535    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2536      lrel = &(p_data->lrdata[v]);      lrel = &(p_data->lrdata[v]);
# Line 2579  static int analyze_make_solvers_lists(st Line 2572  static int analyze_make_solvers_lists(st
2572    
2573    
2574    /*    /*
2575     * process the conditional logrelations      process the conditional logrelations
2576     * for v in logcndlist copy logconddata      for v in logcndlist copy logconddata
2577     */    */
2578    vlen = gl_length(p_data->logcnds);    vlen = gl_length(p_data->logcnds);
2579    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2580      lrel = &(p_data->logcondata[v]);      lrel = &(p_data->logcondata[v]);
# Line 2622  static int analyze_make_solvers_lists(st Line 2615  static int analyze_make_solvers_lists(st
2615    
2616    
2617    /*    /*
2618     * process the boundaries      process the boundaries
2619     * for v in cndlist and logcndlist, copy bnddata.      for v in cndlist and logcndlist, copy bnddata.
2620     */    */
2621    vlen = gl_length(p_data->cnds);    vlen = gl_length(p_data->cnds);
2622    len = gl_length(p_data->logcnds);    len = gl_length(p_data->logcnds);
2623    /* real conditions  */    /* real conditions  */
# Line 2664  static int analyze_make_solvers_lists(st Line 2657  static int analyze_make_solvers_lists(st
2657    p_data->solverbl[vlen+len] = NULL; /* terminator */    p_data->solverbl[vlen+len] = NULL; /* terminator */
2658    
2659    /*    /*
2660     * Finding list of logical relations using the condition, and the      Finding list of logical relations using the condition, and the
2661     * tolerance (only for the case of real condition ). Defining some      tolerance (only for the case of real condition ). Defining some
2662     * flags      flags
2663     */    */
2664    
2665    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2666      bnd = p_data->masterbl[v];      bnd = p_data->masterbl[v];
# Line 2700  static int analyze_make_solvers_lists(st Line 2693  static int analyze_make_solvers_lists(st
2693    }    }
2694    
2695  /*  /*
2696   * for c in whenlist copy whendata.      for c in whenlist copy whendata.
2697   * for c in whenllist set masterwl, solverwl pointer to point to data.      for c in whenllist set masterwl, solverwl pointer to point to data.
2698   */  */
2699    /* process whens */    /* process whens */
2700    
2701    vlen = gl_length(p_data->whens);    vlen = gl_length(p_data->whens);
# Line 2724  static int analyze_make_solvers_lists(st Line 2717  static int analyze_make_solvers_lists(st
2717    p_data->solverwl[vlen] = NULL; /* terminator */    p_data->solverwl[vlen] = NULL; /* terminator */
2718    
2719    /*    /*
2720     * Get data from the when instance to fill the      Get data from the when instance to fill the
2721     * list in the w_when instance      list in the w_when instance
2722     */    */
2723    
2724    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2725      when = p_data->masterwl[v];      when = p_data->masterwl[v];
# Line 2763  static int analyze_make_solvers_lists(st Line 2756  static int analyze_make_solvers_lists(st
2756    } else {    } else {
2757    
2758      /*      /*
2759       * All variables in active relations are set as active.          All variables in active relations are set as active.
2760       * This is necessary because the existence of some variables          This is necessary because the existence of some variables
2761       * in conditional relations which should not be active.          in conditional relations which should not be active.
2762       *  
2763       * Before we were doing:          Before we were doing:
2764       *  
2765       *  for (v = 0;p_data->solvervl[v]!=NULL ; v++) {           for (v = 0;p_data->solvervl[v]!=NULL ; v++) {
2766       *    var = p_data->solvervl[v];             var = p_data->solvervl[v];
2767       *    var_set_active(var,TRUE);             var_set_active(var,TRUE);
2768       *  }           }
2769       *  
2770       *  for (v = 0;p_data->solverdl[v]!=NULL ; v++) {           for (v = 0;p_data->solverdl[v]!=NULL ; v++) {
2771       *    dvar = p_data->solverdl[v];             dvar = p_data->solverdl[v];
2772       *    dis_set_active(dvar,TRUE);             dis_set_active(dvar,TRUE);
2773       *  }           }
2774       *  
2775       * which do not considerate such situation          which do not considerate such situation
2776       */      */
2777    
2778       set_active_vars_in_active_rels(p_data->solverrl);       set_active_vars_in_active_rels(p_data->solverrl);
2779       set_active_vars_in_active_rels(p_data->solverol);       set_active_vars_in_active_rels(p_data->solverol);
2780       set_active_disvars_in_active_logrels(p_data->solverll);       set_active_disvars_in_active_logrels(p_data->solverll);
2781    
2782      /*      /*
2783       * All the unattached are set active to keep an accurate          All the unattached are set active to keep an accurate
2784       * counting in the solver side.          counting in the solver side.
2785       */      */
2786    
2787      for (v = 0;p_data->solverul[v]!=NULL ; v++) {      for (v = 0;p_data->solverul[v]!=NULL ; v++) {
2788        var = p_data->solverul[v];        var = p_data->solverul[v];
# Line 2803  static int analyze_make_solvers_lists(st Line 2796  static int analyze_make_solvers_lists(st
2796    }    }
2797    
2798    /*    /*
2799     * Code to make the variables aware of the relation they are      Code to make the variables aware of the relation they are
2800     * incident in. KHT      incident in. KHT
2801     */    */
2802    vlen = gl_length(p_data->vars);    vlen = gl_length(p_data->vars);
2803    for (v = 0; v < vlen; v++) {    for (v = 0; v < vlen; v++) {
2804      var = &(p_data->vardata[v]);      var = &(p_data->vardata[v]);
# Line 2840  static int analyze_make_solvers_lists(st Line 2833  static int analyze_make_solvers_lists(st
2833    }    }
2834    return 0;    return 0;
2835  }  }
2836    
2837    
2838    
2839  /*  /*
2840   * hand off all the null terminated arrays to slv_system_t.      hand off all the null terminated arrays to slv_system_t.
2841   * Also makes sure all solver_var have been assigned at least once,      Also makes sure all solver_var have been assigned at least once,
2842   * since 0 is a really stupid starting value.      since 0 is a really stupid starting value.
2843   */  */
2844  static  static
2845  int analyze_configure_system(slv_system_t sys,struct problem_t *p_data)  int analyze_configure_system(slv_system_t sys,struct problem_t *p_data)
2846  {  {
# Line 2957  int analyze_configure_system(slv_system_ Line 2950  int analyze_configure_system(slv_system_
2950    p_data->oldips = NULL;    p_data->oldips = NULL;
2951    return 0;    return 0;
2952  }  }
2953    
2954  /*  /*
2955   * fills in a slv_system_t via its object interface from the      fills in a slv_system_t via its object interface from the
2956   * ascend side of the world, establishing any protocols needed to      ascend side of the world, establishing any protocols needed to
2957   * communicate with the instance tree.      communicate with the instance tree.
2958   * Return is 0 if everything ok, nonzero OTHERWISE.      Return is 0 if everything ok, nonzero OTHERWISE.
2959   * 1 = memory      1 = memory
2960   * 2 = bad instance      2 = bad instance
2961   */  */
2962  int analyze_make_problem(slv_system_t sys, struct Instance *inst)  int analyze_make_problem(slv_system_t sys, struct Instance *inst)
2963  {  {
2964    int stat;    int stat;

Legend:
Removed from v.218  
changed lines
  Added in v.219

john.pye@anu.edu.au
ViewVC Help
Powered by ViewVC 1.1.22