1    	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2    	/*                                                                           */
3    	/*                  This file is part of the program and library             */
4    	/*         SCIP --- Solving Constraint Integer Programs                      */
5    	/*                                                                           */
6    	/*  Copyright (c) 2002-2023 Zuse Institute Berlin (ZIB)                      */
7    	/*                                                                           */
8    	/*  Licensed under the Apache License, Version 2.0 (the "License");          */
9    	/*  you may not use this file except in compliance with the License.         */
10   	/*  You may obtain a copy of the License at                                  */
11   	/*                                                                           */
12   	/*      http://www.apache.org/licenses/LICENSE-2.0                           */
13   	/*                                                                           */
14   	/*  Unless required by applicable law or agreed to in writing, software      */
15   	/*  distributed under the License is distributed on an "AS IS" BASIS,        */
16   	/*  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */
17   	/*  See the License for the specific language governing permissions and      */
18   	/*  limitations under the License.                                           */
19   	/*                                                                           */
20   	/*  You should have received a copy of the Apache-2.0 license                */
21   	/*  along with SCIP; see the file LICENSE. If not visit scipopt.org.         */
22   	/*                                                                           */
23   	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
24   	
25   	/**@file   prop.c
26   	 * @ingroup OTHER_CFILES
27   	 * @brief  methods and datastructures for propagators
28   	 * @author Tobias Achterberg
29   	 * @author Timo Berthold
30   	 */
31   	
32   	/*---+----1----+----2----+----3----+----4----+----5----+----6----+----7----+----8----+----9----+----0----+----1----+----2*/
33   	
34   	#include <assert.h>
35   	#include <string.h>
36   	
37   	#include "scip/def.h"
38   	#include "scip/set.h"
39   	#include "scip/stat.h"
40   	#include "scip/clock.h"
41   	#include "scip/paramset.h"
42   	#include "scip/var.h"
43   	#include "scip/scip.h"
44   	#include "scip/prop.h"
45   	#include "scip/pub_message.h"
46   	#include "scip/pub_misc.h"
47   	
48   	#include "scip/struct_prop.h"
49   	
50   	
51   	/** compares two propagators w. r. to their priority */
52   	SCIP_DECL_SORTPTRCOMP(SCIPpropComp)
53   	{  /*lint --e{715}*/
54   	   return ((SCIP_PROP*)elem2)->priority - ((SCIP_PROP*)elem1)->priority;
55   	}
56   	
57   	/** compares two propagators w. r. to their priority */
58   	SCIP_DECL_SORTPTRCOMP(SCIPpropCompPresol)
59   	{  /*lint --e{715}*/
60   	   return ((SCIP_PROP*)elem2)->presolpriority - ((SCIP_PROP*)elem1)->presolpriority;
61   	}
62   	
63   	/** comparison method for sorting propagators w.r.t. to their name */
64   	SCIP_DECL_SORTPTRCOMP(SCIPpropCompName)
65   	{
66   	   return strcmp(SCIPpropGetName((SCIP_PROP*)elem1), SCIPpropGetName((SCIP_PROP*)elem2));
67   	}
68   	
69   	/** method to call, when the priority of a propagator was changed */
70   	static
71   	SCIP_DECL_PARAMCHGD(paramChgdPropPriority)
72   	{  /*lint --e{715}*/
73   	   SCIP_PARAMDATA* paramdata;
74   	
75   	   paramdata = SCIPparamGetData(param);
76   	   assert(paramdata != NULL);
77   	
78   	   /* use SCIPsetPropPriority() to mark the props unsorted */
79   	   SCIP_CALL( SCIPsetPropPriority(scip, (SCIP_PROP*)paramdata, SCIPparamGetInt(param)) ); /*lint !e740*/
80   	
81   	   return SCIP_OKAY;
82   	}
83   	
84   	/** method to call, when the presolving priority of a propagator was changed */
85   	static
86   	SCIP_DECL_PARAMCHGD(paramChgdPropPresolPriority)
87   	{  /*lint --e{715}*/
88   	   SCIP_PARAMDATA* paramdata;
89   	
90   	   paramdata = SCIPparamGetData(param);
91   	   assert(paramdata != NULL);
92   	
93   	   /* use SCIPsetPropPriority() to mark the props unsorted */
94   	   SCIP_CALL( SCIPsetPropPresolPriority(scip, (SCIP_PROP*)paramdata, SCIPparamGetInt(param)) ); /*lint !e740*/
95   	
96   	   return SCIP_OKAY;
97   	}
98   	
99   	/** copies the given propagator to a new scip */
100  	SCIP_RETCODE SCIPpropCopyInclude(
101  	   SCIP_PROP*            prop,               /**< propagator */
102  	   SCIP_SET*             set                 /**< SCIP_SET of SCIP to copy to */
103  	   )
104  	{
105  	   assert(prop != NULL);
106  	   assert(set != NULL);
107  	   assert(set->scip != NULL);
108  	
109  	   if( prop->propcopy != NULL )
110  	   {
111  	      SCIPsetDebugMsg(set, "including propagator %s in subscip %p\n", SCIPpropGetName(prop), (void*)set->scip);
112  	      SCIP_CALL( prop->propcopy(set->scip, prop) );
113  	   }
114  	   return SCIP_OKAY;
115  	}
116  	
117  	/** internal method for creating a propagator */
118  	static
119  	SCIP_RETCODE doPropCreate(
120  	   SCIP_PROP**           prop,               /**< pointer to propagator data structure */
121  	   SCIP_SET*             set,                /**< global SCIP settings */
122  	   SCIP_MESSAGEHDLR*     messagehdlr,        /**< message handler */
123  	   BMS_BLKMEM*           blkmem,             /**< block memory for parameter settings */
124  	   const char*           name,               /**< name of propagator */
125  	   const char*           desc,               /**< description of propagator */
126  	   int                   priority,           /**< priority of the propagator (>= 0: before, < 0: after constraint handlers) */
127  	   int                   freq,               /**< frequency for calling propagator */
128  	   SCIP_Bool             delay,              /**< should propagator be delayed, if other propagators found reductions? */
129  	   SCIP_PROPTIMING       timingmask,         /**< positions in the node solving loop where propagator should be executed */
130  	   int                   presolpriority,     /**< priority of the propagator (>= 0: before, < 0: after constraint handlers) */
131  	   int                   presolmaxrounds,    /**< maximal number of presolving rounds the propagator participates in (-1: no limit) */
132  	   SCIP_PRESOLTIMING     presoltiming,       /**< timing mask of the propagator's presolving method */
133  	   SCIP_DECL_PROPCOPY    ((*propcopy)),      /**< copy method of propagator or NULL if you don't want to copy your plugin into sub-SCIPs */
134  	   SCIP_DECL_PROPFREE    ((*propfree)),      /**< destructor of propagator */
135  	   SCIP_DECL_PROPINIT    ((*propinit)),      /**< initialize propagator */
136  	   SCIP_DECL_PROPEXIT    ((*propexit)),      /**< deinitialize propagator */
137  	   SCIP_DECL_PROPINITPRE ((*propinitpre)),   /**< presolving initialization method of propagator */
138  	   SCIP_DECL_PROPEXITPRE ((*propexitpre)),   /**< presolving deinitialization method of propagator */
139  	   SCIP_DECL_PROPINITSOL ((*propinitsol)),   /**< solving process initialization method of propagator */
140  	   SCIP_DECL_PROPEXITSOL ((*propexitsol)),   /**< solving process deinitialization method of propagator */
141  	   SCIP_DECL_PROPPRESOL  ((*proppresol)),    /**< presolving method */
142  	   SCIP_DECL_PROPEXEC    ((*propexec)),      /**< execution method of propagator */
143  	   SCIP_DECL_PROPRESPROP ((*propresprop)),   /**< propagation conflict resolving method */
144  	   SCIP_PROPDATA*        propdata            /**< propagator data */
145  	   )
146  	{
147  	   char paramname[SCIP_MAXSTRLEN];
148  	   char paramdesc[SCIP_MAXSTRLEN];
149  	
150  	   assert(prop != NULL);
151  	   assert(name != NULL);
152  	   assert(desc != NULL);
153  	   assert(freq >= -1);
154  	   assert(propexec != NULL);
155  	
156  	   /* the interface change from delay flags to timings cannot be recognized at compile time: Exit with an appropriate
157  	    * error message
158  	    */
159  	   if( presoltiming < SCIP_PRESOLTIMING_NONE || presoltiming > SCIP_PRESOLTIMING_MAX )
160  	   {
161  	      SCIPmessagePrintError("ERROR: 'PRESOLDELAY'-flag no longer available since SCIP 3.2, use an appropriate "
162  	         "'SCIP_PRESOLTIMING' for <%s> propagator instead.\n", name);
163  	
164  	      return SCIP_PARAMETERWRONGVAL;
165  	   }
166  	
167  	   SCIP_ALLOC( BMSallocMemory(prop) );
168  	   BMSclearMemory(*prop);
169  	
170  	   SCIP_ALLOC( BMSduplicateMemoryArray(&(*prop)->name, name, strlen(name)+1) );
171  	   SCIP_ALLOC( BMSduplicateMemoryArray(&(*prop)->desc, desc, strlen(desc)+1) );
172  	   (*prop)->priority = priority;
173  	   (*prop)->freq = freq;
174  	   (*prop)->propcopy = propcopy;
175  	   (*prop)->propfree = propfree;
176  	   (*prop)->propinit = propinit;
177  	   (*prop)->propexit = propexit;
178  	   (*prop)->propinitpre = propinitpre;
179  	   (*prop)->propexitpre = propexitpre;
180  	   (*prop)->propinitsol = propinitsol;
181  	   (*prop)->propexitsol = propexitsol;
182  	   (*prop)->proppresol = proppresol;
183  	   (*prop)->propexec = propexec;
184  	   (*prop)->propresprop = propresprop;
185  	   (*prop)->propdata = propdata;
186  	   SCIP_CALL( SCIPclockCreate(&(*prop)->setuptime, SCIP_CLOCKTYPE_DEFAULT) );
187  	   SCIP_CALL( SCIPclockCreate(&(*prop)->proptime, SCIP_CLOCKTYPE_DEFAULT) );
188  	   SCIP_CALL( SCIPclockCreate(&(*prop)->sbproptime, SCIP_CLOCKTYPE_DEFAULT) );
189  	   SCIP_CALL( SCIPclockCreate(&(*prop)->resproptime, SCIP_CLOCKTYPE_DEFAULT) );
190  	   SCIP_CALL( SCIPclockCreate(&(*prop)->presoltime, SCIP_CLOCKTYPE_DEFAULT) );
191  	   (*prop)->ncalls = 0;
192  	   (*prop)->nrespropcalls = 0;
193  	   (*prop)->ncutoffs = 0;
194  	   (*prop)->ndomredsfound = 0;
195  	   (*prop)->wasdelayed = FALSE;
196  	   (*prop)->initialized = FALSE;
197  	
198  	   /* add parameters */
199  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/priority", name);
200  	   (void) SCIPsnprintf(paramdesc, SCIP_MAXSTRLEN, "priority of propagator <%s>", name);
201  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname, paramdesc,
202  	         &(*prop)->priority, TRUE, priority, INT_MIN/4, INT_MAX/4,
203  	         paramChgdPropPriority, (SCIP_PARAMDATA*)(*prop)) ); /*lint !e740*/
204  	
205  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/freq", name);
206  	   (void) SCIPsnprintf(paramdesc, SCIP_MAXSTRLEN, "frequency for calling propagator <%s> (-1: never, 0: only in root node)", name);
207  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname, paramdesc,
208  	         &(*prop)->freq, FALSE, freq, -1, SCIP_MAXTREEDEPTH, NULL, NULL) );
209  	
210  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/delay", name);
211  	   SCIP_CALL( SCIPsetAddBoolParam(set, messagehdlr, blkmem, paramname,
212  	         "should propagator be delayed, if other propagators found reductions?",
213  	         &(*prop)->delay, TRUE, delay, NULL, NULL) ); /*lint !e740*/
214  	
215  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/timingmask", name);
216  	   (void) SCIPsnprintf(paramdesc, SCIP_MAXSTRLEN, "timing when propagator should be called (%u:BEFORELP, %u:DURINGLPLOOP, %u:AFTERLPLOOP, %u:ALWAYS))",
217  	      SCIP_PROPTIMING_BEFORELP, SCIP_PROPTIMING_DURINGLPLOOP, SCIP_PROPTIMING_AFTERLPLOOP, SCIP_PROPTIMING_ALWAYS);
218  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname, paramdesc,
219  	         (int*)(&(*prop)->timingmask), TRUE, (int) timingmask, (int) SCIP_PROPTIMING_BEFORELP, (int) SCIP_PROPTIMING_ALWAYS, NULL, NULL) ); /*lint !e713*/
220  	
221  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/presolpriority", name);
222  	   (void) SCIPsnprintf(paramdesc, SCIP_MAXSTRLEN, "presolving priority of propagator <%s>", name);
223  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname, paramdesc,
224  	         &(*prop)->presolpriority, TRUE, presolpriority, INT_MIN/4, INT_MAX/4,
225  	         paramChgdPropPresolPriority, (SCIP_PARAMDATA*)(*prop)) ); /*lint !e740*/
226  	
227  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/maxprerounds", name);
228  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname,
229  	         "maximal number of presolving rounds the propagator participates in (-1: no limit)",
230  	         &(*prop)->maxprerounds, FALSE, presolmaxrounds, -1, INT_MAX, NULL, NULL) ); /*lint !e740*/
231  	
232  	   (void) SCIPsnprintf(paramname, SCIP_MAXSTRLEN, "propagating/%s/presoltiming", name);
233  	   (void) SCIPsnprintf(paramdesc, SCIP_MAXSTRLEN, "timing mask of the presolving method of propagator <%s> (%u:FAST, %u:MEDIUM, %u:EXHAUSTIVE, %u:FINAL)",
234  	      name, SCIP_PRESOLTIMING_FAST, SCIP_PRESOLTIMING_MEDIUM, SCIP_PRESOLTIMING_EXHAUSTIVE, SCIP_PRESOLTIMING_FINAL);
235  	   SCIP_CALL( SCIPsetAddIntParam(set, messagehdlr, blkmem, paramname, paramdesc,
236  	         (int*)&(*prop)->presoltiming, TRUE, (int)presoltiming, (int) SCIP_PRESOLTIMING_NONE, (int) SCIP_PRESOLTIMING_MAX, NULL, NULL) ); /*lint !e740*/
237  	
238  	   return SCIP_OKAY;
239  	}
240  	
241  	/** creates a propagator */
242  	SCIP_RETCODE SCIPpropCreate(
243  	   SCIP_PROP**           prop,               /**< pointer to propagator data structure */
244  	   SCIP_SET*             set,                /**< global SCIP settings */
245  	   SCIP_MESSAGEHDLR*     messagehdlr,        /**< message handler */
246  	   BMS_BLKMEM*           blkmem,             /**< block memory for parameter settings */
247  	   const char*           name,               /**< name of propagator */
248  	   const char*           desc,               /**< description of propagator */
249  	   int                   priority,           /**< priority of the propagator (>= 0: before, < 0: after constraint handlers) */
250  	   int                   freq,               /**< frequency for calling propagator */
251  	   SCIP_Bool             delay,              /**< should propagator be delayed, if other propagators found reductions? */
252  	   SCIP_PROPTIMING       timingmask,         /**< positions in the node solving loop where propagator should be executed */
253  	   int                   presolpriority,     /**< priority of the propagator (>= 0: before, < 0: after constraint handlers) */
254  	   int                   presolmaxrounds,    /**< maximal number of presolving rounds the propagator participates in (-1: no limit) */
255  	   SCIP_PRESOLTIMING     presoltiming,       /**< timing mask of the propagator's presolving method */
256  	   SCIP_DECL_PROPCOPY    ((*propcopy)),      /**< copy method of propagator or NULL if you don't want to copy your plugin into sub-SCIPs */
257  	   SCIP_DECL_PROPFREE    ((*propfree)),      /**< destructor of propagator */
258  	   SCIP_DECL_PROPINIT    ((*propinit)),      /**< initialize propagator */
259  	   SCIP_DECL_PROPEXIT    ((*propexit)),      /**< deinitialize propagator */
260  	   SCIP_DECL_PROPINITPRE ((*propinitpre)),   /**< presolving initialization method of propagator */
261  	   SCIP_DECL_PROPEXITPRE ((*propexitpre)),   /**< presolving deinitialization method of propagator */
262  	   SCIP_DECL_PROPINITSOL ((*propinitsol)),   /**< solving process initialization method of propagator */
263  	   SCIP_DECL_PROPEXITSOL ((*propexitsol)),   /**< solving process deinitialization method of propagator */
264  	   SCIP_DECL_PROPPRESOL  ((*proppresol)),    /**< presolving method */
265  	   SCIP_DECL_PROPEXEC    ((*propexec)),      /**< execution method of propagator */
266  	   SCIP_DECL_PROPRESPROP ((*propresprop)),   /**< propagation conflict resolving method */
267  	   SCIP_PROPDATA*        propdata            /**< propagator data */
268  	   )
269  	{
270  	   assert(prop != NULL);
271  	   assert(name != NULL);
272  	   assert(desc != NULL);
273  	   assert(freq >= -1);
274  	   assert(propexec != NULL);
275  	
276  	   SCIP_CALL_FINALLY( doPropCreate(prop, set, messagehdlr, blkmem, name, desc, priority, freq, delay, timingmask,
277  	      presolpriority, presolmaxrounds, presoltiming, propcopy, propfree, propinit, propexit, propinitpre, propexitpre,
278  	      propinitsol, propexitsol, proppresol, propexec, propresprop, propdata), (void) SCIPpropFree(prop, set) );
279  	
280  	   return SCIP_OKAY;
281  	}
282  	
283  	/** calls destructor and frees memory of propagator */
284  	SCIP_RETCODE SCIPpropFree(
285  	   SCIP_PROP**           prop,               /**< pointer to propagator data structure */
286  	   SCIP_SET*             set                 /**< global SCIP settings */
287  	   )
288  	{
289  	   assert(prop != NULL);
290  	   if( *prop == NULL )
291  	      return SCIP_OKAY;
292  	   assert(!(*prop)->initialized);
293  	   assert(set != NULL);
294  	
295  	   /* call destructor of propagator */
296  	   if( (*prop)->propfree != NULL )
297  	   {
298  	      SCIP_CALL( (*prop)->propfree(set->scip, *prop) );
299  	   }
300  	
301  	   SCIPclockFree(&(*prop)->presoltime);
302  	   SCIPclockFree(&(*prop)->resproptime);
303  	   SCIPclockFree(&(*prop)->sbproptime);
304  	   SCIPclockFree(&(*prop)->proptime);
305  	   SCIPclockFree(&(*prop)->setuptime);
306  	   BMSfreeMemoryArrayNull(&(*prop)->desc);
307  	   BMSfreeMemoryArrayNull(&(*prop)->name);
308  	   BMSfreeMemory(prop);
309  	
310  	   return SCIP_OKAY;
311  	}
312  	
313  	/** initializes propagator */
314  	SCIP_RETCODE SCIPpropInit(
315  	   SCIP_PROP*            prop,               /**< propagator */
316  	   SCIP_SET*             set                 /**< global SCIP settings */
317  	   )
318  	{
319  	   assert(prop != NULL);
320  	   assert(set != NULL);
321  	
322  	   if( prop->initialized )
323  	   {
324  	      SCIPerrorMessage("propagator <%s> already initialized\n", prop->name);
325  	      return SCIP_INVALIDCALL;
326  	   }
327  	
328  	   if( set->misc_resetstat )
329  	   {
330  	      SCIPclockReset(prop->proptime);
331  	      SCIPclockReset(prop->sbproptime);
332  	      SCIPclockReset(prop->resproptime);
333  	      SCIPclockReset(prop->presoltime);
334  	      SCIPclockReset(prop->setuptime);
335  	
336  	      prop->ncalls = 0;
337  	      prop->nrespropcalls = 0;
338  	      prop->ncutoffs = 0;
339  	      prop->ndomredsfound = 0;
340  	      prop->lastnfixedvars = 0;
341  	      prop->lastnaggrvars = 0;
342  	      prop->lastnchgvartypes = 0;
343  	      prop->lastnchgbds = 0;
344  	      prop->lastnaddholes = 0;
345  	      prop->lastndelconss = 0;
346  	      prop->lastnaddconss = 0;
347  	      prop->lastnupgdconss = 0;
348  	      prop->lastnchgcoefs = 0;
349  	      prop->lastnchgsides = 0;
350  	      prop->nfixedvars = 0;
351  	      prop->naggrvars = 0;
352  	      prop->nchgvartypes = 0;
353  	      prop->nchgbds = 0;
354  	      prop->naddholes = 0;
355  	      prop->ndelconss = 0;
356  	      prop->naddconss = 0;
357  	      prop->nupgdconss = 0;
358  	      prop->nchgcoefs = 0;
359  	      prop->nchgsides = 0;
360  	      prop->npresolcalls = 0;
361  	      prop->wasdelayed = FALSE;
362  	   }
363  	
364  	   if( prop->propinit != NULL )
365  	   {
366  	      /* start timing */
367  	      SCIPclockStart(prop->setuptime, set);
368  	
369  	      SCIP_CALL( prop->propinit(set->scip, prop) );
370  	
371  	      /* stop timing */
372  	      SCIPclockStop(prop->setuptime, set);
373  	   }
374  	   prop->initialized = TRUE;
375  	
376  	   return SCIP_OKAY;
377  	}
378  	
379  	/** calls exit method of propagator */
380  	SCIP_RETCODE SCIPpropExit(
381  	   SCIP_PROP*            prop,               /**< propagator */
382  	   SCIP_SET*             set                 /**< global SCIP settings */
383  	   )
384  	{
385  	   assert(prop != NULL);
386  	   assert(set != NULL);
387  	
388  	   if( !prop->initialized )
389  	   {
390  	      SCIPerrorMessage("propagator <%s> not initialized\n", prop->name);
391  	      return SCIP_INVALIDCALL;
392  	   }
393  	
394  	   if( prop->propexit != NULL )
395  	   {
396  	      /* start timing */
397  	      SCIPclockStart(prop->setuptime, set);
398  	
399  	      SCIP_CALL( prop->propexit(set->scip, prop) );
400  	
401  	      /* stop timing */
402  	      SCIPclockStop(prop->setuptime, set);
403  	   }
404  	   prop->initialized = FALSE;
405  	
406  	   return SCIP_OKAY;
407  	}
408  	
409  	/** informs propagator that the presolving process is being started */
410  	SCIP_RETCODE SCIPpropInitpre(
411  	   SCIP_PROP*            prop,               /**< propagator */
412  	   SCIP_SET*             set                 /**< global SCIP settings */
413  	   )
414  	{
415  	   assert(prop != NULL);
416  	   assert(set != NULL);
417  	
418  	   prop->lastnfixedvars = 0;
419  	   prop->lastnaggrvars = 0;
420  	   prop->lastnchgvartypes = 0;
421  	   prop->lastnchgbds = 0;
422  	   prop->lastnaddholes = 0;
423  	   prop->lastndelconss = 0;
424  	   prop->lastnaddconss = 0;
425  	   prop->lastnupgdconss = 0;
426  	   prop->lastnchgcoefs = 0;
427  	   prop->lastnchgsides = 0;
428  	   prop->wasdelayed = FALSE;
429  	
430  	   /* call presolving initialization method of propagator */
431  	   if( prop->propinitpre != NULL )
432  	   {
433  	      /* start timing */
434  	      SCIPclockStart(prop->setuptime, set);
435  	
436  	      SCIP_CALL( prop->propinitpre(set->scip, prop) );
437  	
438  	      /* stop timing */
439  	      SCIPclockStop(prop->setuptime, set);
440  	   }
441  	
442  	   return SCIP_OKAY;
443  	}
444  	
445  	/** informs propagator that the presolving process is finished */
446  	SCIP_RETCODE SCIPpropExitpre(
447  	   SCIP_PROP*            prop,               /**< propagator */
448  	   SCIP_SET*             set                 /**< global SCIP settings */
449  	   )
450  	{
451  	   assert(prop != NULL);
452  	   assert(set != NULL);
453  	
454  	   /* call presolving deinitialization method of propagator */
455  	   if( prop->propexitpre != NULL )
456  	   {
457  	      /* start timing */
458  	      SCIPclockStart(prop->setuptime, set);
459  	
460  	      SCIP_CALL( prop->propexitpre(set->scip, prop) );
461  	
462  	      /* stop timing */
463  	      SCIPclockStop(prop->setuptime, set);
464  	   }
465  	
466  	   return SCIP_OKAY;
467  	}
468  	
469  	/** informs propagator that the prop and bound process is being started */
470  	SCIP_RETCODE SCIPpropInitsol(
471  	   SCIP_PROP*            prop,               /**< propagator */
472  	   SCIP_SET*             set                 /**< global SCIP settings */
473  	   )
474  	{
475  	   assert(prop != NULL);
476  	   assert(set != NULL);
477  	
478  	   /* call solving process initialization method of propagator */
479  	   if( prop->propinitsol != NULL )
480  	   {
481  	      /* start timing */
482  	      SCIPclockStart(prop->setuptime, set);
483  	
484  	      SCIP_CALL( prop->propinitsol(set->scip, prop) );
485  	
486  	      /* stop timing */
487  	      SCIPclockStop(prop->setuptime, set);
488  	   }
489  	
490  	   return SCIP_OKAY;
491  	}
492  	
493  	/** informs propagator that the prop and bound process data is being freed */
494  	SCIP_RETCODE SCIPpropExitsol(
495  	   SCIP_PROP*            prop,               /**< propagator */
496  	   SCIP_SET*             set,                /**< global SCIP settings */
497  	   SCIP_Bool             restart             /**< was this exit solve call triggered by a restart? */
498  	   )
499  	{
500  	   assert(prop != NULL);
501  	   assert(set != NULL);
502  	
503  	   /* call solving process deinitialization method of propagator */
504  	   if( prop->propexitsol != NULL )
505  	   {
506  	      /* start timing */
507  	      SCIPclockStart(prop->setuptime, set);
508  	
509  	      SCIP_CALL( prop->propexitsol(set->scip, prop, restart) );
510  	
511  	      /* stop timing */
512  	      SCIPclockStop(prop->setuptime, set);
513  	   }
514  	
515  	   return SCIP_OKAY;
516  	}
517  	
518  	/** executes presolving method of propagator */
519  	SCIP_RETCODE SCIPpropPresol(
520  	   SCIP_PROP*            prop,               /**< propagator */
521  	   SCIP_SET*             set,                /**< global SCIP settings */
522  	   SCIP_PRESOLTIMING     timing,             /**< current presolving timing */
523  	   int                   nrounds,            /**< number of presolving rounds already done */
524  	   int*                  nfixedvars,         /**< pointer to total number of variables fixed of all presolvers */
525  	   int*                  naggrvars,          /**< pointer to total number of variables aggregated of all presolvers */
526  	   int*                  nchgvartypes,       /**< pointer to total number of variable type changes of all presolvers */
527  	   int*                  nchgbds,            /**< pointer to total number of variable bounds tightened of all presolvers */
528  	   int*                  naddholes,          /**< pointer to total number of domain holes added of all presolvers */
529  	   int*                  ndelconss,          /**< pointer to total number of deleted constraints of all presolvers */
530  	   int*                  naddconss,          /**< pointer to total number of added constraints of all presolvers */
531  	   int*                  nupgdconss,         /**< pointer to total number of upgraded constraints of all presolvers */
532  	   int*                  nchgcoefs,          /**< pointer to total number of changed coefficients of all presolvers */
533  	   int*                  nchgsides,          /**< pointer to total number of changed left/right hand sides of all presolvers */
534  	   SCIP_RESULT*          result              /**< pointer to store the result of the callback method */
535  	   )
536  	{
537  	   assert(prop != NULL);
538  	   assert(set != NULL);
539  	   assert(nfixedvars != NULL);
540  	   assert(naggrvars != NULL);
541  	   assert(nchgvartypes != NULL);
542  	   assert(nchgbds != NULL);
543  	   assert(naddholes != NULL);
544  	   assert(ndelconss != NULL);
545  	   assert(naddconss != NULL);
546  	   assert(nupgdconss != NULL);
547  	   assert(nchgcoefs != NULL);
548  	   assert(nchgsides != NULL);
549  	   assert(result != NULL);
550  	
551  	   *result = SCIP_DIDNOTRUN;
552  	
553  	   if( prop->proppresol == NULL )
554  	      return SCIP_OKAY;
555  	
556  	   /* check number of presolving rounds */
557  	   if( prop->maxprerounds >= 0 && prop->npresolcalls >= prop->maxprerounds )
558  	      return SCIP_OKAY;
559  	
560  	   /* check, if presolver should be delayed */
561  	   if( prop->presoltiming & timing )
562  	   {
563  	      int nnewfixedvars;
564  	      int nnewaggrvars;
565  	      int nnewchgvartypes;
566  	      int nnewchgbds;
567  	      int nnewaddholes;
568  	      int nnewdelconss;
569  	      int nnewaddconss;
570  	      int nnewupgdconss;
571  	      int nnewchgcoefs;
572  	      int nnewchgsides;
573  	
574  	      SCIPsetDebugMsg(set, "calling presolving method of propagator <%s>\n", prop->name);
575  	
576  	      /* calculate the number of changes since last call */
577  	      nnewfixedvars = *nfixedvars - prop->lastnfixedvars;
578  	      nnewaggrvars = *naggrvars - prop->lastnaggrvars;
579  	      nnewchgvartypes = *nchgvartypes - prop->lastnchgvartypes;
580  	      nnewchgbds = *nchgbds - prop->lastnchgbds;
581  	      nnewaddholes = *naddholes - prop->lastnaddholes;
582  	      nnewdelconss = *ndelconss - prop->lastndelconss;
583  	      nnewaddconss = *naddconss - prop->lastnaddconss;
584  	      nnewupgdconss = *nupgdconss - prop->lastnupgdconss;
585  	      nnewchgcoefs = *nchgcoefs - prop->lastnchgcoefs;
586  	      nnewchgsides = *nchgsides - prop->lastnchgsides;
587  	
588  	      /* remember the number of changes prior to the call of the presolver method of the propagator */
589  	      prop->lastnfixedvars = *nfixedvars;
590  	      prop->lastnaggrvars = *naggrvars;
591  	      prop->lastnchgvartypes = *nchgvartypes;
592  	      prop->lastnchgbds = *nchgbds;
593  	      prop->lastnaddholes = *naddholes;
594  	      prop->lastndelconss = *ndelconss;
595  	      prop->lastnaddconss = *naddconss;
596  	      prop->lastnupgdconss = *nupgdconss;
597  	      prop->lastnchgcoefs = *nchgcoefs;
598  	      prop->lastnchgsides = *nchgsides;
599  	
600  	      /* start timing */
601  	      SCIPclockStart(prop->presoltime, set);
602  	
603  	      /* call external method */
604  	      SCIP_CALL( prop->proppresol(set->scip, prop, nrounds, timing,
605  	            nnewfixedvars, nnewaggrvars, nnewchgvartypes, nnewchgbds, nnewaddholes,
606  	            nnewdelconss, nnewaddconss, nnewupgdconss, nnewchgcoefs, nnewchgsides,
607  	            nfixedvars, naggrvars, nchgvartypes, nchgbds, naddholes,
608  	            ndelconss, naddconss, nupgdconss, nchgcoefs, nchgsides, result) );
609  	
610  	      /* stop timing */
611  	      SCIPclockStop(prop->presoltime, set);
612  	
613  	      /* add/count the new changes */
614  	      prop->nfixedvars += *nfixedvars - prop->lastnfixedvars;
615  	      prop->naggrvars += *naggrvars - prop->lastnaggrvars;
616  	      prop->nchgvartypes += *nchgvartypes - prop->lastnchgvartypes;
617  	      prop->nchgbds += *nchgbds - prop->lastnchgbds;
618  	      prop->naddholes += *naddholes - prop->lastnaddholes;
619  	      prop->ndelconss += *ndelconss - prop->lastndelconss;
620  	      prop->naddconss += *naddconss - prop->lastnaddconss;
621  	      prop->nupgdconss += *nupgdconss - prop->lastnupgdconss;
622  	      prop->nchgcoefs += *nchgcoefs - prop->lastnchgcoefs;
623  	      prop->nchgsides += *nchgsides - prop->lastnchgsides;
624  	
625  	      /* check result code of callback method */
626  	      if( *result != SCIP_CUTOFF
627  	         && *result != SCIP_UNBOUNDED
628  	         && *result != SCIP_SUCCESS
629  	         && *result != SCIP_DIDNOTFIND
630  	         && *result != SCIP_DIDNOTRUN )
631  	      {
632  	         SCIPerrorMessage("propagator <%s> returned invalid result <%d>\n", prop->name, *result);
633  	         return SCIP_INVALIDRESULT;
634  	      }
635  	
636  	      /* increase the number of presolving calls, if the propagator tried to find reductions */
637  	      if( *result != SCIP_DIDNOTRUN )
638  	         ++(prop->npresolcalls);
639  	   }
640  	
641  	   return SCIP_OKAY;
642  	}
643  	
644  	/** calls execution method of propagator */
645  	SCIP_RETCODE SCIPpropExec(
646  	   SCIP_PROP*            prop,               /**< propagator */
647  	   SCIP_SET*             set,                /**< global SCIP settings */
648  	   SCIP_STAT*            stat,               /**< dynamic problem statistics */
649  	   int                   depth,              /**< depth of current node */
650  	   SCIP_Bool             execdelayed,        /**< execute propagator even if it is marked to be delayed */
651  	   SCIP_Bool             instrongbranching,  /**< are we currently doing strong branching? */
652  	   SCIP_PROPTIMING       proptiming,         /**< current point in the node solving process */
653  	   SCIP_RESULT*          result              /**< pointer to store the result of the callback method */
654  	   )
655  	{
656  	   assert(prop != NULL);
657  	   assert(prop->propexec != NULL);
658  	   assert(prop->freq >= -1);
659  	   assert(set != NULL);
660  	   assert(set->scip != NULL);
661  	   assert(stat != NULL);
662  	   assert(depth >= 0);
663  	   assert(result != NULL);
664  	
665  	   if( (depth == 0 && prop->freq == 0) || (prop->freq > 0 && depth % prop->freq == 0) )
666  	   {
667  	      if( !prop->delay || execdelayed )
668  	      {
669  	         SCIP_Longint oldndomchgs;
670  	         SCIP_Longint oldnprobdomchgs;
671  	
672  	         SCIPsetDebugMsg(set, "executing propagator <%s>\n", prop->name);
673  	
674  	         oldndomchgs = stat->nboundchgs + stat->nholechgs;
675  	         oldnprobdomchgs = stat->nprobboundchgs + stat->nprobholechgs;
676  	
677  	         /* start timing */
678  	         if( instrongbranching )
679  	            SCIPclockStart(prop->sbproptime, set);
680  	         else
681  	            SCIPclockStart(prop->proptime, set);
682  	
683  	         /* call external propagation method */
684  	         SCIP_CALL( prop->propexec(set->scip, prop, proptiming, result) );
685  	
686  	         /* stop timing */
687  	         if( instrongbranching )
688  	            SCIPclockStop(prop->sbproptime, set);
689  	         else
690  	            SCIPclockStop(prop->proptime, set);
691  	
692  	         /* update statistics */
693  	         if( *result != SCIP_DIDNOTRUN && *result != SCIP_DELAYED )
694  	            prop->ncalls++;
695  	         if( *result == SCIP_CUTOFF )
696  	            prop->ncutoffs++;
697  	
698  	         /* update domain reductions; therefore remove the domain
699  	          * reduction counts which were generated in probing mode */
700  	         prop->ndomredsfound += stat->nboundchgs + stat->nholechgs - oldndomchgs;
701  	         prop->ndomredsfound -= (stat->nprobboundchgs + stat->nprobholechgs - oldnprobdomchgs);
702  	
703  	         /* evaluate result */
704  	         if( *result != SCIP_CUTOFF
705  	            && *result != SCIP_REDUCEDDOM
706  	            && *result != SCIP_DIDNOTFIND
707  	            && *result != SCIP_DIDNOTRUN
708  	            && *result != SCIP_DELAYED
709  	            && *result != SCIP_DELAYNODE )
710  	         {
711  	            SCIPerrorMessage("execution method of propagator <%s> returned invalid result <%d>\n",
712  	               prop->name, *result);
713  	            return SCIP_INVALIDRESULT;
714  	         }
715  	      }
716  	      else
717  	      {
718  	         SCIPsetDebugMsg(set, "propagator <%s> was delayed\n", prop->name);
719  	         *result = SCIP_DELAYED;
720  	      }
721  	
722  	      /* remember whether propagator was delayed */
723  	      prop->wasdelayed = (*result == SCIP_DELAYED);
724  	   }
725  	   else
726  	      *result = SCIP_DIDNOTRUN;
727  	
728  	   return SCIP_OKAY;
729  	}
730  	
731  	/** resolves the given conflicting bound, that was deduced by the given propagator, by putting all "reason" bounds
732  	 *  leading to the deduction into the conflict queue with calls to SCIPaddConflictLb(), SCIPaddConflictUb(), SCIPaddConflictBd(),
733  	 *  SCIPaddConflictRelaxedLb(), SCIPaddConflictRelaxedUb(), SCIPaddConflictRelaxedBd(), or SCIPaddConflictBinvar();
734  	 *
735  	 *  @note it is sufficient to explain the relaxed bound change
736  	 */
737  	SCIP_RETCODE SCIPpropResolvePropagation(
738  	   SCIP_PROP*            prop,               /**< propagator */
739  	   SCIP_SET*             set,                /**< global SCIP settings */
740  	   SCIP_VAR*             infervar,           /**< variable whose bound was deduced by the constraint */
741  	   int                   inferinfo,          /**< user inference information attached to the bound change */
742  	   SCIP_BOUNDTYPE        inferboundtype,     /**< bound that was deduced (lower or upper bound) */
743  	   SCIP_BDCHGIDX*        bdchgidx,           /**< bound change index, representing the point of time where change took place */
744  	   SCIP_Real             relaxedbd,          /**< the relaxed bound */
745  	   SCIP_RESULT*          result              /**< pointer to store the result of the callback method */
746  	   )
747  	{
748  	   assert(prop != NULL);
749  	   assert((inferboundtype == SCIP_BOUNDTYPE_LOWER
750  	         && SCIPgetVarLbAtIndex(set->scip, infervar, bdchgidx, TRUE) > SCIPvarGetLbGlobal(infervar))
751  	      || (inferboundtype == SCIP_BOUNDTYPE_UPPER
752  	         && SCIPgetVarUbAtIndex(set->scip, infervar, bdchgidx, TRUE) < SCIPvarGetUbGlobal(infervar)));
753  	   assert(result != NULL);
754  	
755  	   *result = SCIP_DIDNOTRUN;
756  	
757  	   if( prop->propresprop != NULL )
758  	   {
759  	      /* start timing */
760  	      SCIPclockStart(prop->resproptime, set);
761  	
762  	      SCIP_CALL( prop->propresprop(set->scip, prop, infervar, inferinfo, inferboundtype, bdchgidx,
763  	            relaxedbd, result) );
764  	
765  	      /* stop timing */
766  	      SCIPclockStop(prop->resproptime, set);
767  	
768  	      /* update statistic */
769  	      prop->nrespropcalls++;
770  	
771  	      /* check result code */
772  	      if( *result != SCIP_SUCCESS && *result != SCIP_DIDNOTFIND )
773  	      {
774  	         SCIPerrorMessage("propagation conflict resolving method of propagator <%s> returned invalid result <%d>\n",
775  	            prop->name, *result);
776  	         return SCIP_INVALIDRESULT;
777  	      }
778  	   }
779  	   else
780  	   {
781  	      SCIPerrorMessage("propagation conflict resolving method of propagator <%s> is not implemented\n", prop->name);
782  	      return SCIP_PLUGINNOTFOUND;
783  	   }
784  	
785  	   return SCIP_OKAY;
786  	}
787  	
788  	/** gets user data of propagator */
789  	SCIP_PROPDATA* SCIPpropGetData(
790  	   SCIP_PROP*            prop                /**< propagator */
791  	   )
792  	{
793  	   assert(prop != NULL);
794  	
795  	   return prop->propdata;
796  	}
797  	
798  	/** sets user data of propagator; user has to free old data in advance! */
799  	void SCIPpropSetData(
800  	   SCIP_PROP*            prop,               /**< propagator */
801  	   SCIP_PROPDATA*        propdata            /**< new propagator user data */
802  	   )
803  	{
804  	   assert(prop != NULL);
805  	
806  	   prop->propdata = propdata;
807  	}
808  	
809  	/** sets copy method of propagator */
810  	void SCIPpropSetCopy(
811  	   SCIP_PROP*            prop,               /**< propagator */
812  	   SCIP_DECL_PROPCOPY    ((*propcopy))       /**< copy method of propagator or NULL if you don't want to copy your plugin into sub-SCIPs */
813  	   )
814  	{
815  	   assert(prop != NULL);
816  	
817  	   prop->propcopy = propcopy;
818  	}
819  	
820  	/** sets destructor method of propagator */
821  	void SCIPpropSetFree(
822  	   SCIP_PROP*            prop,               /**< propagator */
823  	   SCIP_DECL_PROPFREE    ((*propfree))       /**< destructor of propagator */
824  	   )
825  	{
826  	   assert(prop != NULL);
827  	
828  	   prop->propfree = propfree;
829  	}
830  	
831  	/** sets initialization method of propagator */
832  	void SCIPpropSetInit(
833  	   SCIP_PROP*            prop,               /**< propagator */
834  	   SCIP_DECL_PROPINIT    ((*propinit))       /**< initialize propagator */
835  	   )
836  	{
837  	   assert(prop != NULL);
838  	
839  	   prop->propinit = propinit;
840  	}
841  	
842  	/** sets deinitialization method of propagator */
843  	void SCIPpropSetExit(
844  	   SCIP_PROP*            prop,               /**< propagator */
845  	   SCIP_DECL_PROPEXIT    ((*propexit))       /**< deinitialize propagator */
846  	   )
847  	{
848  	   assert(prop != NULL);
849  	
850  	   prop->propexit = propexit;
851  	}
852  	
853  	/** sets solving process initialization method of propagator */
854  	void SCIPpropSetInitsol(
855  	   SCIP_PROP*            prop,               /**< propagator */
856  	   SCIP_DECL_PROPINITSOL((*propinitsol))     /**< solving process initialization method of propagator */
857  	   )
858  	{
859  	   assert(prop != NULL);
860  	
861  	   prop->propinitsol = propinitsol;
862  	}
863  	
864  	/** sets solving process deinitialization method of propagator */
865  	void SCIPpropSetExitsol(
866  	   SCIP_PROP*            prop,               /**< propagator */
867  	   SCIP_DECL_PROPEXITSOL ((*propexitsol))    /**< solving process deinitialization method of propagator */
868  	   )
869  	{
870  	   assert(prop != NULL);
871  	
872  	   prop->propexitsol = propexitsol;
873  	}
874  	
875  	/** sets preprocessing initialization method of propagator */
876  	void SCIPpropSetInitpre(
877  	   SCIP_PROP*            prop,               /**< propagator */
878  	   SCIP_DECL_PROPINITPRE((*propinitpre))     /**< preprocessing initialization method of propagator */
879  	   )
880  	{
881  	   assert(prop != NULL);
882  	
883  	   prop->propinitpre = propinitpre;
884  	}
885  	
886  	
887  	
888  	/** sets preprocessing deinitialization method of propagator */
889  	void SCIPpropSetExitpre(
890  	   SCIP_PROP*            prop,               /**< propagator */
891  	   SCIP_DECL_PROPEXITPRE((*propexitpre))     /**< preprocessing deinitialization method of propagator */
892  	   )
893  	{
894  	   assert(prop != NULL);
895  	
896  	   prop->propexitpre = propexitpre;
897  	}
898  	
899  	/** sets presolving method of propagator */
900  	SCIP_RETCODE SCIPpropSetPresol(
901  	   SCIP_PROP*            prop,               /**< propagator */
902  	   SCIP_DECL_PROPPRESOL  ((*proppresol)),    /**< presolving method */
903  	   int                   presolpriority,     /**< presolving priority of the propagator (>= 0: before, < 0: after constraint handlers) */
904  	   int                   presolmaxrounds,    /**< maximal number of presolving rounds the propagator participates in (-1: no limit) */
905  	   SCIP_PRESOLTIMING     presoltiming        /**< timing mask of the propagator's presolving method */
906  	   )
907  	{
908  	   assert(prop != NULL);
909  	
910  	   prop->proppresol = proppresol;
911  	   prop->presolpriority = presolpriority;
912  	   /* the interface change from delay flags to timings cannot be recognized at compile time: Exit with an appropriate
913  	    * error message
914  	    */
915  	   if( presoltiming < SCIP_PRESOLTIMING_FAST || presoltiming > SCIP_PRESOLTIMING_MAX )
916  	   {
917  	      SCIPmessagePrintError("ERROR: 'PRESOLDELAY'-flag no longer available since SCIP 3.2, use an appropriate "
918  	         "'SCIP_PRESOLTIMING' for <%s> constraint handler instead.\n", prop->name);
919  	
920  	      return SCIP_PARAMETERWRONGVAL;
921  	   }
922  	
923  	   prop->presoltiming = presoltiming;
924  	   prop->maxprerounds = presolmaxrounds;
925  	
926  	   return SCIP_OKAY;
927  	}
928  	
929  	/** sets propagation conflict resolving callback of propagator */
930  	void SCIPpropSetResprop(
931  	   SCIP_PROP*            prop,               /**< propagator */
932  	   SCIP_DECL_PROPRESPROP ((*propresprop))    /**< propagation conflict resolving callback */
933  	   )
934  	{
935  	   assert(prop != NULL);
936  	
937  	   prop->propresprop = propresprop;
938  	}
939  	
940  	/** gets name of propagator */
941  	const char* SCIPpropGetName(
942  	   SCIP_PROP*            prop                /**< propagator */
943  	   )
944  	{
945  	   assert(prop != NULL);
946  	
947  	   return prop->name;
948  	}
949  	
950  	/** gets description of propagator */
951  	const char* SCIPpropGetDesc(
952  	   SCIP_PROP*            prop                /**< propagator */
953  	   )
954  	{
955  	   assert(prop != NULL);
956  	
957  	   return prop->desc;
958  	}
959  	
960  	/** gets priority of propagator */
961  	int SCIPpropGetPriority(
962  	   SCIP_PROP*            prop                /**< propagator */
963  	   )
964  	{
965  	   assert(prop != NULL);
966  	
967  	   return prop->priority;
968  	}
969  	
970  	/** gets presolving priority of propagator */
971  	int SCIPpropGetPresolPriority(
972  	   SCIP_PROP*            prop                /**< propagator */
973  	   )
974  	{
975  	   assert(prop != NULL);
976  	
977  	   return prop->presolpriority;
978  	}
979  	
980  	/** sets priority of propagator */
981  	void SCIPpropSetPriority(
982  	   SCIP_PROP*            prop,               /**< propagator */
983  	   SCIP_SET*             set,                /**< global SCIP settings */
984  	   int                   priority            /**< new priority of the propagator */
985  	   )
986  	{
987  	   assert(prop != NULL);
988  	   assert(set != NULL);
989  	
990  	   prop->priority = priority;
991  	   set->propssorted = FALSE;
992  	}
993  	
994  	/** sets presolving priority of propagator */
995  	void SCIPpropSetPresolPriority(
996  	   SCIP_PROP*            prop,               /**< propagator */
997  	   SCIP_SET*             set,                /**< global SCIP settings */
998  	   int                   presolpriority      /**< new priority of the propagator */
999  	   )
1000 	{
1001 	   assert(prop != NULL);
1002 	   assert(set != NULL);
1003 	
1004 	   prop->presolpriority = presolpriority;
1005 	   set->propspresolsorted = FALSE;
1006 	}
1007 	
1008 	/** gets frequency of propagator */
1009 	int SCIPpropGetFreq(
1010 	   SCIP_PROP*            prop                /**< propagator */
1011 	   )
1012 	{
1013 	   assert(prop != NULL);
1014 	
1015 	   return prop->freq;
1016 	}
1017 	
1018 	/** enables or disables all clocks of \p prop, depending on the value of the flag */
1019 	void SCIPpropEnableOrDisableClocks(
1020 	   SCIP_PROP*            prop,               /**< the propagator for which all clocks should be enabled or disabled */
1021 	   SCIP_Bool             enable              /**< should the clocks of the propagator be enabled? */
1022 	   )
1023 	{
1024 	   assert(prop != NULL);
1025 	
1026 	   SCIPclockEnableOrDisable(prop->setuptime, enable);
1027 	   SCIPclockEnableOrDisable(prop->presoltime, enable);
1028 	   SCIPclockEnableOrDisable(prop->proptime, enable);
1029 	   SCIPclockEnableOrDisable(prop->resproptime, enable);
1030 	   SCIPclockEnableOrDisable(prop->sbproptime, enable);
1031 	}
1032 	
1033 	/** gets time in seconds used for setting up this propagator for new stages */
1034 	SCIP_Real SCIPpropGetSetupTime(
1035 	   SCIP_PROP*            prop                /**< propagator */
1036 	   )
1037 	{
1038 	   assert(prop != NULL);
1039 	
1040 	   return SCIPclockGetTime(prop->setuptime);
1041 	}
1042 	
1043 	/** sets frequency of propagator */
1044 	void SCIPpropSetFreq(
1045 	   SCIP_PROP*            prop,               /**< propagator */
1046 	   int                   freq                /**< new frequency of propagator */
1047 	   )
1048 	{
1049 	   assert(prop != NULL);
1050 	   assert(freq >= -1);
1051 	
1052 	   prop->freq = freq;
1053 	}
1054 	
1055 	/** gets time in seconds used in this propagator for propagation */
1056 	SCIP_Real SCIPpropGetTime(
1057 	   SCIP_PROP*            prop                /**< propagator */
1058 	   )
1059 	{
1060 	   assert(prop != NULL);
1061 	
1062 	   return SCIPclockGetTime(prop->proptime);
1063 	}
1064 	
1065 	/** gets time in seconds used in this propagator for propagation during strong branching */
1066 	SCIP_Real SCIPpropGetStrongBranchPropTime(
1067 	   SCIP_PROP*            prop                /**< propagator */
1068 	   )
1069 	{
1070 	   assert(prop != NULL);
1071 	
1072 	   return SCIPclockGetTime(prop->sbproptime);
1073 	}
1074 	
1075 	/** gets time in seconds used in this propagator for resolve propagation */
1076 	SCIP_Real SCIPpropGetRespropTime(
1077 	   SCIP_PROP*            prop                /**< propagator */
1078 	   )
1079 	{
1080 	   assert(prop != NULL);
1081 	
1082 	   return SCIPclockGetTime(prop->resproptime);
1083 	}
1084 	
1085 	/** gets time in seconds used in this propagator for presolving */
1086 	SCIP_Real SCIPpropGetPresolTime(
1087 	   SCIP_PROP*            prop                /**< propagator */
1088 	   )
1089 	{
1090 	   assert(prop != NULL);
1091 	
1092 	   return SCIPclockGetTime(prop->presoltime);
1093 	}
1094 	
1095 	/** gets the total number of times, the propagator was called */
1096 	SCIP_Longint SCIPpropGetNCalls(
1097 	   SCIP_PROP*            prop                /**< propagator */
1098 	   )
1099 	{
1100 	   assert(prop != NULL);
1101 	
1102 	   return prop->ncalls;
1103 	}
1104 	
1105 	/** gets the total number of times, the propagator was called for resolving a propagation */
1106 	SCIP_Longint SCIPpropGetNRespropCalls(
1107 	   SCIP_PROP*            prop                /**< propagator */
1108 	   )
1109 	{
1110 	   assert(prop != NULL);
1111 	
1112 	   return prop->nrespropcalls;
1113 	}
1114 	
1115 	/** gets total number of times, this propagator detected a cutoff */
1116 	SCIP_Longint SCIPpropGetNCutoffs(
1117 	   SCIP_PROP*            prop                /**< propagator */
1118 	   )
1119 	{
1120 	   assert(prop != NULL);
1121 	
1122 	   return prop->ncutoffs;
1123 	}
1124 	
1125 	/** gets total number of domain reductions found by this propagator */
1126 	SCIP_Longint SCIPpropGetNDomredsFound(
1127 	   SCIP_PROP*            prop                /**< propagator */
1128 	   )
1129 	{
1130 	   assert(prop != NULL);
1131 	
1132 	   return prop->ndomredsfound;
1133 	}
1134 	
1135 	/** should propagator be delayed, if other propagators found reductions? */
1136 	SCIP_Bool SCIPpropIsDelayed(
1137 	   SCIP_PROP*            prop                /**< propagator */
1138 	   )
1139 	{
1140 	   assert(prop != NULL);
1141 	
1142 	   return prop->delay;
1143 	}
1144 	
1145 	/** was propagator delayed at the last call? */
1146 	SCIP_Bool SCIPpropWasDelayed(
1147 	   SCIP_PROP*            prop                /**< propagator */
1148 	   )
1149 	{
1150 	   assert(prop != NULL);
1151 	
1152 	   return prop->wasdelayed;
1153 	}
1154 	
1155 	/** is propagator initialized? */
1156 	SCIP_Bool SCIPpropIsInitialized(
1157 	   SCIP_PROP*            prop                /**< propagator */
1158 	   )
1159 	{
1160 	   assert(prop != NULL);
1161 	
1162 	   return prop->initialized;
1163 	}
1164 	
1165 	/** gets number of variables fixed during presolving of propagator */
1166 	int SCIPpropGetNFixedVars(
1167 	   SCIP_PROP*            prop                /**< propagator */
1168 	   )
1169 	{
1170 	   assert(prop != NULL);
1171 	
1172 	   return prop->nfixedvars;
1173 	}
1174 	
1175 	/** gets number of variables aggregated during presolving of propagator  */
1176 	int SCIPpropGetNAggrVars(
1177 	   SCIP_PROP*            prop                /**< propagator */
1178 	   )
1179 	{
1180 	   assert(prop != NULL);
1181 	
1182 	   return prop->naggrvars;
1183 	}
1184 	
1185 	/** gets number of variable types changed during presolving of propagator  */
1186 	int SCIPpropGetNChgVarTypes(
1187 	   SCIP_PROP*            prop                /**< propagator */
1188 	   )
1189 	{
1190 	   assert(prop != NULL);
1191 	
1192 	   return prop->nchgvartypes;
1193 	}
1194 	
1195 	/** gets number of bounds changed during presolving of propagator  */
1196 	int SCIPpropGetNChgBds(
1197 	   SCIP_PROP*            prop                /**< propagator */
1198 	   )
1199 	{
1200 	   assert(prop != NULL);
1201 	
1202 	   return prop->nchgbds;
1203 	}
1204 	
1205 	/** gets number of holes added to domains of variables during presolving of propagator  */
1206 	int SCIPpropGetNAddHoles(
1207 	   SCIP_PROP*            prop                /**< propagator */
1208 	   )
1209 	{
1210 	   assert(prop != NULL);
1211 	
1212 	   return prop->naddholes;
1213 	}
1214 	
1215 	/** gets number of constraints deleted during presolving of propagator */
1216 	int SCIPpropGetNDelConss(
1217 	   SCIP_PROP*            prop                /**< propagator */
1218 	   )
1219 	{
1220 	   assert(prop != NULL);
1221 	
1222 	   return prop->ndelconss;
1223 	}
1224 	
1225 	/** gets number of constraints added during presolving of propagator */
1226 	int SCIPpropGetNAddConss(
1227 	   SCIP_PROP*            prop                /**< propagator */
1228 	   )
1229 	{
1230 	   assert(prop != NULL);
1231 	
1232 	   return prop->naddconss;
1233 	}
1234 	
1235 	/** gets number of constraints upgraded during presolving of propagator  */
1236 	int SCIPpropGetNUpgdConss(
1237 	   SCIP_PROP*            prop                /**< propagator */
1238 	   )
1239 	{
1240 	   assert(prop != NULL);
1241 	
1242 	   return prop->nupgdconss;
1243 	}
1244 	
1245 	/** gets number of coefficients changed during presolving of propagator */
1246 	int SCIPpropGetNChgCoefs(
1247 	   SCIP_PROP*            prop                /**< propagator */
1248 	   )
1249 	{
1250 	   assert(prop != NULL);
1251 	
1252 	   return prop->nchgcoefs;
1253 	}
1254 	
1255 	/** gets number of constraint sides changed during presolving of propagator */
1256 	int SCIPpropGetNChgSides(
1257 	   SCIP_PROP*            prop                /**< propagator */
1258 	   )
1259 	{
1260 	   assert(prop != NULL);
1261 	
1262 	   return prop->nchgsides;
1263 	}
1264 	
1265 	/** gets number of times the propagator was called in presolving and tried to find reductions */
1266 	int SCIPpropGetNPresolCalls(
1267 	   SCIP_PROP*            prop                /**< propagator */
1268 	   )
1269 	{
1270 	   assert(prop != NULL);
1271 	
1272 	   return prop->npresolcalls;
1273 	}
1274 	
1275 	/** returns the timing mask of the propagator */
1276 	SCIP_PROPTIMING SCIPpropGetTimingmask(
1277 	   SCIP_PROP*            prop                /**< propagator */
1278 	   )
1279 	{
1280 	   assert(prop != NULL);
1281 	
1282 	   return prop->timingmask;
1283 	}
1284 	
1285 	/** does the propagator perform presolving? */
1286 	SCIP_Bool SCIPpropDoesPresolve(
1287 	   SCIP_PROP*            prop                /**< propagator */
1288 	   )
1289 	{
1290 	   assert(prop != NULL);
1291 	
1292 	   return (prop->proppresol != NULL);
1293 	}
1294 	
1295 	/** returns the timing mask of the presolving method of the propagator */
1296 	SCIP_PRESOLTIMING SCIPpropGetPresolTiming(
1297 	   SCIP_PROP*            prop                /**< propagator */
1298 	   )
1299 	{
1300 	   assert(prop != NULL);
1301 	
1302 	   return prop->presoltiming;
1303 	}
1304 	
1305 	/** sets the timing mask of the presolving method of the propagator */
1306 	void SCIPpropSetPresolTiming(
1307 	   SCIP_PROP*            prop,               /**< propagator */
1308 	   SCIP_PRESOLTIMING     presoltiming        /** timing mask to be set */
1309 	   )
1310 	{
1311 	   assert(prop != NULL);
1312 	
1313 	   prop->presoltiming = presoltiming;
1314 	}
1315