aboutsummaryrefslogtreecommitdiffstats
path: root/test/monniaux/glpk-4.65/examples
diff options
context:
space:
mode:
authorDavid Monniaux <david.monniaux@univ-grenoble-alpes.fr>2020-03-03 08:17:40 +0100
committerDavid Monniaux <david.monniaux@univ-grenoble-alpes.fr>2020-03-03 08:17:40 +0100
commit1ab7b51c30e1b10ac45b0bd64cefdc01da0f7f68 (patch)
tree210ffc156c83f04fb0c61a40b4f9037d7ba8a7e1 /test/monniaux/glpk-4.65/examples
parent222c9047d61961db9c6b19fed5ca49829223fd33 (diff)
parent12be46d59a2483a10d77fa8ee67f7e0ca1bd702f (diff)
downloadcompcert-kvx-1ab7b51c30e1b10ac45b0bd64cefdc01da0f7f68.tar.gz
compcert-kvx-1ab7b51c30e1b10ac45b0bd64cefdc01da0f7f68.zip
Merge branch 'mppa-cse2' of gricad-gitlab.univ-grenoble-alpes.fr:sixcy/CompCert into mppa-work
Diffstat (limited to 'test/monniaux/glpk-4.65/examples')
-rw-r--r--test/monniaux/glpk-4.65/examples/glpsol.c1598
-rw-r--r--test/monniaux/glpk-4.65/examples/prod.mod331
2 files changed, 1929 insertions, 0 deletions
diff --git a/test/monniaux/glpk-4.65/examples/glpsol.c b/test/monniaux/glpk-4.65/examples/glpsol.c
new file mode 100644
index 00000000..17df3380
--- /dev/null
+++ b/test/monniaux/glpk-4.65/examples/glpsol.c
@@ -0,0 +1,1598 @@
+/* glpsol.c (stand-alone GLPK LP/MIP solver) */
+
+/***********************************************************************
+* This code is part of GLPK (GNU Linear Programming Kit).
+*
+* Copyright (C) 2000-2017 Andrew Makhorin, Department for Applied
+* Informatics, Moscow Aviation Institute, Moscow, Russia. All rights
+* reserved. E-mail: <mao@gnu.org>.
+*
+* GLPK is free software: you can redistribute it and/or modify it
+* under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* GLPK is distributed in the hope that it will be useful, but WITHOUT
+* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
+* License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with GLPK. If not, see <http://www.gnu.org/licenses/>.
+***********************************************************************/
+
+#define VERIMAG
+#ifdef VERIMAG
+#include "../../clock.h"
+#endif
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include <ctype.h>
+#include <float.h>
+#include <limits.h>
+#include <math.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <glpk.h>
+
+#define xassert glp_assert
+#define xerror glp_error
+#define xprintf glp_printf
+
+struct csa
+{ /* common storage area */
+ glp_prob *prob;
+ /* LP/MIP problem object */
+ glp_bfcp bfcp;
+ /* basis factorization control parameters */
+ glp_smcp smcp;
+ /* simplex method control parameters */
+ glp_iptcp iptcp;
+ /* interior-point method control parameters */
+ glp_iocp iocp;
+ /* integer optimizer control parameters */
+ glp_tran *tran;
+ /* model translator workspace */
+ glp_graph *graph;
+ /* network problem object */
+ int format;
+ /* problem file format: */
+#define FMT_MPS_DECK 1 /* fixed MPS */
+#define FMT_MPS_FILE 2 /* free MPS */
+#define FMT_LP 3 /* CPLEX LP */
+#define FMT_GLP 4 /* GLPK LP/MIP */
+#define FMT_MATHPROG 5 /* MathProg */
+#define FMT_MIN_COST 6 /* DIMACS min-cost flow */
+#define FMT_MAX_FLOW 7 /* DIMACS maximum flow */
+#if 1 /* 06/VIII-2011 */
+#define FMT_CNF 8 /* DIMACS CNF-SAT */
+#endif
+ const char *in_file;
+ /* name of input problem file */
+#define DATA_MAX 10
+ /* maximal number of input data files */
+ int ndf;
+ /* number of input data files specified */
+ const char *in_data[1+DATA_MAX];
+ /* name(s) of input data file(s) */
+ const char *out_dpy;
+ /* name of output file to send display output; NULL means the
+ display output is sent to the terminal */
+ int seed;
+ /* seed value to be passed to the MathProg translator; initially
+ set to 1; 0x80000000 means the value is omitted */
+ int solution;
+ /* solution type flag: */
+#define SOL_BASIC 1 /* basic */
+#define SOL_INTERIOR 2 /* interior-point */
+#define SOL_INTEGER 3 /* mixed integer */
+ const char *in_res;
+ /* name of input solution file in raw format */
+ int dir;
+ /* optimization direction flag:
+ 0 - not specified
+ GLP_MIN - minimization
+ GLP_MAX - maximization */
+ int scale;
+ /* automatic problem scaling flag */
+ const char *out_sol;
+ /* name of output solution file in printable format */
+ const char *out_res;
+ /* name of output solution file in raw format */
+ const char *out_ranges;
+ /* name of output file to write sensitivity analysis report */
+ int check;
+ /* input data checking flag; no solution is performed */
+ const char *new_name;
+ /* new name to be assigned to the problem */
+#if 1 /* 18/I-2018 */
+ int hide;
+ /* clear all symbolic names in the problem object */
+#endif
+ const char *out_mps;
+ /* name of output problem file in fixed MPS format */
+ const char *out_freemps;
+ /* name of output problem file in free MPS format */
+ const char *out_cpxlp;
+ /* name of output problem file in CPLEX LP format */
+ const char *out_glp;
+ /* name of output problem file in GLPK format */
+#if 0
+ const char *out_pb;
+ /* name of output problem file in OPB format */
+ const char *out_npb;
+ /* name of output problem file in normalized OPB format */
+#endif
+#if 1 /* 06/VIII-2011 */
+ const char *out_cnf;
+ /* name of output problem file in DIMACS CNF-SAT format */
+#endif
+ const char *log_file;
+ /* name of output file to hardcopy terminal output */
+ int crash;
+ /* initial basis option: */
+#define USE_STD_BASIS 1 /* use standard basis */
+#define USE_ADV_BASIS 2 /* use advanced basis */
+#define USE_CPX_BASIS 3 /* use Bixby's basis */
+#define USE_INI_BASIS 4 /* use initial basis from ini_file */
+ const char *ini_file;
+ /* name of input file containing initial basis */
+ int exact;
+ /* flag to use glp_exact rather than glp_simplex */
+ int xcheck;
+ /* flag to check final basis with glp_exact */
+ int nomip;
+ /* flag to consider MIP as pure LP */
+#if 1 /* 15/VIII-2011 */
+ int minisat;
+ /* option to solve feasibility problem with MiniSat solver */
+ int use_bnd;
+ /* option to bound objective function */
+ int obj_bnd;
+ /* upper (minization) or lower (maximization) objective bound */
+#endif
+#if 1 /* 11/VII-2013 */
+ const char *use_sol;
+ /* name of input mip solution file in GLPK format */
+#endif
+};
+
+static int str2int(const char *s, int *x)
+{ /* convert string to integer */
+ long t;
+ char *endptr;
+ t = strtol(s, &endptr, 10);
+ if (*endptr != '\0')
+ return 2;
+ if (!(INT_MIN <= t && t <= INT_MAX))
+ return 1;
+ *x = t;
+#if 0
+ xprintf("str2int: x = %d\n", *x);
+#endif
+ return 0;
+}
+
+static int str2num(const char *s, double *x)
+{ /* convert string to floating point */
+ double t;
+ char *endptr;
+ t = strtod(s, &endptr);
+ if (*endptr != '\0')
+ return 2;
+ if (!(-DBL_MAX <= t && t <= +DBL_MAX))
+ return 1;
+ *x = t;
+#if 0
+ xprintf("str2num: x = %g\n", *x);
+#endif
+ return 0;
+}
+
+static void print_help(const char *my_name)
+{ /* print help information */
+ xprintf("Usage: %s [options...] filename\n", my_name);
+ xprintf("\n");
+ xprintf("General options:\n");
+ xprintf(" --mps read LP/MIP problem in fixed MPS fo"
+ "rmat\n");
+ xprintf(" --freemps read LP/MIP problem in free MPS for"
+ "mat (default)\n");
+ xprintf(" --lp read LP/MIP problem in CPLEX LP for"
+ "mat\n");
+ xprintf(" --glp read LP/MIP problem in GLPK format "
+ "\n");
+ xprintf(" --math read LP/MIP model written in GNU Ma"
+ "thProg modeling\n");
+ xprintf(" language\n");
+ xprintf(" -m filename, --model filename\n");
+ xprintf(" read model section and optional dat"
+ "a section from\n");
+ xprintf(" filename (same as --math)\n");
+ xprintf(" -d filename, --data filename\n");
+ xprintf(" read data section from filename (fo"
+ "r --math only);\n");
+ xprintf(" if model file also has data section"
+ ", it is ignored\n");
+ xprintf(" -y filename, --display filename\n");
+ xprintf(" send display output to filename (fo"
+ "r --math only);\n");
+ xprintf(" by default the output is sent to te"
+ "rminal\n");
+ xprintf(" --seed value initialize pseudo-random number gen"
+ "erator used in\n");
+ xprintf(" MathProg model with specified seed "
+ "(any integer);\n");
+ xprintf(" if seed value is ?, some random see"
+ "d will be used\n");
+ xprintf(" --mincost read min-cost flow problem in DIMAC"
+ "S format\n");
+ xprintf(" --maxflow read maximum flow problem in DIMACS"
+ " format\n");
+#if 1 /* 06/VIII-2011 */
+ xprintf(" --cnf read CNF-SAT problem in DIMACS form"
+ "at\n");
+#endif
+ xprintf(" --simplex use simplex method (default)\n");
+ xprintf(" --interior use interior point method (LP only)"
+ "\n");
+ xprintf(" -r filename, --read filename\n");
+ xprintf(" read solution from filename rather "
+ "to find it with\n");
+ xprintf(" the solver\n");
+ xprintf(" --min minimization\n");
+ xprintf(" --max maximization\n");
+ xprintf(" --scale scale problem (default)\n");
+ xprintf(" --noscale do not scale problem\n");
+ xprintf(" -o filename, --output filename\n");
+ xprintf(" write solution to filename in print"
+ "able format\n");
+ xprintf(" -w filename, --write filename\n");
+ xprintf(" write solution to filename in plain"
+ " text format\n");
+ xprintf(" --ranges filename\n");
+ xprintf(" write sensitivity analysis report t"
+ "o filename in\n");
+ xprintf(" printable format (simplex only)\n");
+ xprintf(" --tmlim nnn limit solution time to nnn seconds "
+ "\n");
+ xprintf(" --memlim nnn limit available memory to nnn megab"
+ "ytes\n");
+ xprintf(" --check do not solve problem, check input d"
+ "ata only\n");
+ xprintf(" --name probname change problem name to probname\n");
+#if 1 /* 18/I-2018 */
+ xprintf(" --hide remove all symbolic names from prob"
+ "lem object\n");
+#endif
+ xprintf(" --wmps filename write problem to filename in fixed "
+ "MPS format\n");
+ xprintf(" --wfreemps filename\n");
+ xprintf(" write problem to filename in free M"
+ "PS format\n");
+ xprintf(" --wlp filename write problem to filename in CPLEX "
+ "LP format\n");
+ xprintf(" --wglp filename write problem to filename in GLPK f"
+ "ormat\n");
+#if 0
+ xprintf(" --wpb filename write problem to filename in OPB fo"
+ "rmat\n");
+ xprintf(" --wnpb filename write problem to filename in normal"
+ "ized OPB format\n");
+#endif
+#if 1 /* 06/VIII-2011 */
+ xprintf(" --wcnf filename write problem to filename in DIMACS"
+ " CNF-SAT format\n");
+#endif
+ xprintf(" --log filename write copy of terminal output to fi"
+ "lename\n");
+ xprintf(" -h, --help display this help information and e"
+ "xit\n");
+ xprintf(" -v, --version display program version and exit\n")
+ ;
+ xprintf("\n");
+ xprintf("LP basis factorization options:\n");
+#if 0 /* 08/III-2014 */
+ xprintf(" --luf LU + Forrest-Tomlin update\n");
+ xprintf(" (faster, less stable; default)\n");
+ xprintf(" --cbg LU + Schur complement + Bartels-Gol"
+ "ub update\n");
+ xprintf(" (slower, more stable)\n");
+ xprintf(" --cgr LU + Schur complement + Givens rota"
+ "tion update\n");
+ xprintf(" (slower, more stable)\n");
+#else
+ xprintf(" --luf plain LU-factorization (default)\n")
+ ;
+ xprintf(" --btf block triangular LU-factorization\n"
+ );
+ xprintf(" --ft Forrest-Tomlin update (requires --l"
+ "uf; default)\n");
+ xprintf(" --cbg Schur complement + Bartels-Golub up"
+ "date\n");
+ xprintf(" --cgr Schur complement + Givens rotation "
+ "update\n");
+#endif
+ xprintf("\n");
+ xprintf("Options specific to simplex solver:\n");
+ xprintf(" --primal use primal simplex (default)\n");
+ xprintf(" --dual use dual simplex\n");
+ xprintf(" --std use standard initial basis of all s"
+ "lacks\n");
+ xprintf(" --adv use advanced initial basis (default"
+ ")\n");
+ xprintf(" --bib use Bixby's initial basis\n");
+ xprintf(" --ini filename use as initial basis previously sav"
+ "ed with -w\n");
+ xprintf(" (disables LP presolver)\n");
+ xprintf(" --steep use steepest edge technique (defaul"
+ "t)\n");
+ xprintf(" --nosteep use standard \"textbook\" pricing\n"
+ );
+ xprintf(" --relax use Harris' two-pass ratio test (de"
+ "fault)\n");
+ xprintf(" --norelax use standard \"textbook\" ratio tes"
+ "t\n");
+#if 0 /* 23/VI-2017 */
+#if 1 /* 28/III-2016 */
+ xprintf(" --flip use flip-flop ratio test (assumes -"
+ "-dual)\n");
+#endif
+#else
+ /* now this option is implemented in both primal and dual */
+ xprintf(" --flip use long-step ratio test\n");
+#endif
+ xprintf(" --presol use presolver (default; assumes --s"
+ "cale and --adv)\n");
+ xprintf(" --nopresol do not use presolver\n");
+ xprintf(" --exact use simplex method based on exact a"
+ "rithmetic\n");
+ xprintf(" --xcheck check final basis using exact arith"
+ "metic\n");
+ xprintf("\n");
+ xprintf("Options specific to interior-point solver:\n");
+ xprintf(" --nord use natural (original) ordering\n");
+ xprintf(" --qmd use quotient minimum degree orderin"
+ "g\n");
+ xprintf(" --amd use approximate minimum degree orde"
+ "ring (default)\n");
+ xprintf(" --symamd use approximate minimum degree orde"
+ "ring\n");
+ xprintf("\n");
+ xprintf("Options specific to MIP solver:\n");
+ xprintf(" --nomip consider all integer variables as c"
+ "ontinuous\n");
+ xprintf(" (allows solving MIP as pure LP)\n");
+ xprintf(" --first branch on first integer variable\n")
+ ;
+ xprintf(" --last branch on last integer variable\n");
+ xprintf(" --mostf branch on most fractional variable "
+ "\n");
+ xprintf(" --drtom branch using heuristic by Driebeck "
+ "and Tomlin\n");
+ xprintf(" (default)\n");
+ xprintf(" --pcost branch using hybrid pseudocost heur"
+ "istic (may be\n");
+ xprintf(" useful for hard instances)\n");
+ xprintf(" --dfs backtrack using depth first search "
+ "\n");
+ xprintf(" --bfs backtrack using breadth first searc"
+ "h\n");
+ xprintf(" --bestp backtrack using the best projection"
+ " heuristic\n");
+ xprintf(" --bestb backtrack using node with best loca"
+ "l bound\n");
+ xprintf(" (default)\n");
+ xprintf(" --intopt use MIP presolver (default)\n");
+ xprintf(" --nointopt do not use MIP presolver\n");
+ xprintf(" --binarize replace general integer variables b"
+ "y binary ones\n");
+ xprintf(" (assumes --intopt)\n");
+ xprintf(" --fpump apply feasibility pump heuristic\n")
+ ;
+#if 1 /* 29/VI-2013 */
+ xprintf(" --proxy [nnn] apply proximity search heuristic (n"
+ "nn is time limit\n");
+ xprintf(" in seconds; default is 60)\n");
+#endif
+ xprintf(" --gomory generate Gomory's mixed integer cut"
+ "s\n");
+ xprintf(" --mir generate MIR (mixed integer roundin"
+ "g) cuts\n");
+ xprintf(" --cover generate mixed cover cuts\n");
+ xprintf(" --clique generate clique cuts\n");
+ xprintf(" --cuts generate all cuts above\n");
+ xprintf(" --mipgap tol set relative mip gap tolerance to t"
+ "ol\n");
+#if 1 /* 15/VIII-2011 */
+ xprintf(" --minisat translate integer feasibility probl"
+ "em to CNF-SAT\n");
+ xprintf(" and solve it with MiniSat solver\n")
+ ;
+ xprintf(" --objbnd bound add inequality obj <= bound (minimi"
+ "zation) or\n");
+ xprintf(" obj >= bound (maximization) to inte"
+ "ger feasibility\n");
+ xprintf(" problem (assumes --minisat)\n");
+#endif
+ xprintf("\n");
+ xprintf("For description of the MPS and CPLEX LP formats see Refe"
+ "rence Manual.\n");
+ xprintf("For description of the modeling language see \"GLPK: Mod"
+ "eling Language\n");
+ xprintf("GNU MathProg\". Both documents are included in the GLPK "
+ "distribution.\n");
+ xprintf("\n");
+ xprintf("See GLPK web page at <http://www.gnu.org/software/glpk/g"
+ "lpk.html>.\n");
+ xprintf("\n");
+ xprintf("Please report bugs to <bug-glpk@gnu.org>.\n");
+ return;
+}
+
+static void print_version(int briefly)
+{ /* print version information */
+ xprintf("GLPSOL: GLPK LP/MIP Solver, v%s\n", glp_version());
+ if (briefly) goto done;
+ xprintf("Copyright (C) 2000-2017 Andrew Makhorin, Department for "
+ "Applied\n");
+ xprintf("Informatics, Moscow Aviation Institute, Moscow, Russia. "
+ "All rights\n");
+ xprintf("reserved. E-mail: <mao@gnu.org>.\n");
+ xprintf("\n");
+ xprintf("This program has ABSOLUTELY NO WARRANTY.\n");
+ xprintf("\n");
+ xprintf("This program is free software; you may re-distribute it "
+ "under the terms\n");
+ xprintf("of the GNU General Public License version 3 or later.\n")
+ ;
+done: return;
+}
+
+static int parse_cmdline(struct csa *csa, int argc, char *argv[])
+{ /* parse command-line parameters */
+ int k;
+#define p(str) (strcmp(argv[k], str) == 0)
+ for (k = 1; k < argc; k++)
+ { if (p("--mps"))
+ csa->format = FMT_MPS_DECK;
+ else if (p("--freemps"))
+ csa->format = FMT_MPS_FILE;
+ else if (p("--lp") || p("--cpxlp"))
+ csa->format = FMT_LP;
+ else if (p("--glp"))
+ csa->format = FMT_GLP;
+ else if (p("--math") || p("-m") || p("--model"))
+ csa->format = FMT_MATHPROG;
+ else if (p("-d") || p("--data"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No input data file specified\n");
+ return 1;
+ }
+ if (csa->ndf == DATA_MAX)
+ { xprintf("Too many input data files\n");
+ return 1;
+ }
+ csa->in_data[++(csa->ndf)] = argv[k];
+ }
+ else if (p("-y") || p("--display"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No display output file specified\n");
+ return 1;
+ }
+ if (csa->out_dpy != NULL)
+ { xprintf("Only one display output file allowed\n");
+ return 1;
+ }
+ csa->out_dpy = argv[k];
+ }
+ else if (p("--seed"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' ||
+ argv[k][0] == '-' && !isdigit((unsigned char)argv[k][1]))
+ { xprintf("No seed value specified\n");
+ return 1;
+ }
+ if (strcmp(argv[k], "?") == 0)
+ csa->seed = 0x80000000;
+ else if (str2int(argv[k], &csa->seed))
+ { xprintf("Invalid seed value '%s'\n", argv[k]);
+ return 1;
+ }
+ }
+ else if (p("--mincost"))
+ csa->format = FMT_MIN_COST;
+ else if (p("--maxflow"))
+ csa->format = FMT_MAX_FLOW;
+#if 1 /* 06/VIII-2011 */
+ else if (p("--cnf"))
+ csa->format = FMT_CNF;
+#endif
+ else if (p("--simplex"))
+ csa->solution = SOL_BASIC;
+ else if (p("--interior"))
+ csa->solution = SOL_INTERIOR;
+#if 1 /* 28/V-2010 */
+ else if (p("--alien"))
+ csa->iocp.alien = GLP_ON;
+#endif
+ else if (p("-r") || p("--read"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No input solution file specified\n");
+ return 1;
+ }
+ if (csa->in_res != NULL)
+ { xprintf("Only one input solution file allowed\n");
+ return 1;
+ }
+ csa->in_res = argv[k];
+ }
+ else if (p("--min"))
+ csa->dir = GLP_MIN;
+ else if (p("--max"))
+ csa->dir = GLP_MAX;
+ else if (p("--scale"))
+ csa->scale = 1;
+ else if (p("--noscale"))
+ csa->scale = 0;
+ else if (p("-o") || p("--output"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No output solution file specified\n");
+ return 1;
+ }
+ if (csa->out_sol != NULL)
+ { xprintf("Only one output solution file allowed\n");
+ return 1;
+ }
+ csa->out_sol = argv[k];
+ }
+ else if (p("-w") || p("--write"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No output solution file specified\n");
+ return 1;
+ }
+ if (csa->out_res != NULL)
+ { xprintf("Only one output solution file allowed\n");
+ return 1;
+ }
+ csa->out_res = argv[k];
+ }
+ else if (p("--ranges") || p("--bounds"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No output file specified to write sensitivity a"
+ "nalysis report\n");
+ return 1;
+ }
+ if (csa->out_ranges != NULL)
+ { xprintf("Only one output file allowed to write sensitivi"
+ "ty analysis report\n");
+ return 1;
+ }
+ csa->out_ranges = argv[k];
+ }
+ else if (p("--tmlim"))
+ { int tm_lim;
+ k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No time limit specified\n");
+ return 1;
+ }
+ if (str2int(argv[k], &tm_lim) || tm_lim < 0)
+ { xprintf("Invalid time limit '%s'\n", argv[k]);
+ return 1;
+ }
+ if (tm_lim <= INT_MAX / 1000)
+ csa->smcp.tm_lim = csa->iocp.tm_lim = 1000 * tm_lim;
+ else
+ csa->smcp.tm_lim = csa->iocp.tm_lim = INT_MAX;
+ }
+ else if (p("--memlim"))
+ { int mem_lim;
+ k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No memory limit specified\n");
+ return 1;
+ }
+ if (str2int(argv[k], &mem_lim) || mem_lim < 1)
+ { xprintf("Invalid memory limit '%s'\n", argv[k]);
+ return 1;
+ }
+ glp_mem_limit(mem_lim);
+ }
+ else if (p("--check"))
+ csa->check = 1;
+ else if (p("--name"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No problem name specified\n");
+ return 1;
+ }
+ if (csa->new_name != NULL)
+ { xprintf("Only one problem name allowed\n");
+ return 1;
+ }
+ csa->new_name = argv[k];
+ }
+#if 1 /* 18/I-2018 */
+ else if (p("--hide"))
+ csa->hide = 1;
+#endif
+ else if (p("--wmps"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No fixed MPS output file specified\n");
+ return 1;
+ }
+ if (csa->out_mps != NULL)
+ { xprintf("Only one fixed MPS output file allowed\n");
+ return 1;
+ }
+ csa->out_mps = argv[k];
+ }
+ else if (p("--wfreemps"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No free MPS output file specified\n");
+ return 1;
+ }
+ if (csa->out_freemps != NULL)
+ { xprintf("Only one free MPS output file allowed\n");
+ return 1;
+ }
+ csa->out_freemps = argv[k];
+ }
+ else if (p("--wlp") || p("--wcpxlp") || p("--wlpt"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No CPLEX LP output file specified\n");
+ return 1;
+ }
+ if (csa->out_cpxlp != NULL)
+ { xprintf("Only one CPLEX LP output file allowed\n");
+ return 1;
+ }
+ csa->out_cpxlp = argv[k];
+ }
+ else if (p("--wglp"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No GLPK LP/MIP output file specified\n");
+ return 1;
+ }
+ if (csa->out_glp != NULL)
+ { xprintf("Only one GLPK LP/MIP output file allowed\n");
+ return 1;
+ }
+ csa->out_glp = argv[k];
+ }
+#if 0
+ else if (p("--wpb"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No problem output file specified\n");
+ return 1;
+ }
+ if (csa->out_pb != NULL)
+ { xprintf("Only one OPB output file allowed\n");
+ return 1;
+ }
+ csa->out_pb = argv[k];
+ }
+ else if (p("--wnpb"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No problem output file specified\n");
+ return 1;
+ }
+ if (csa->out_npb != NULL)
+ { xprintf("Only one normalized OPB output file allowed\n");
+ return 1;
+ }
+ csa->out_npb = argv[k];
+ }
+#endif
+#if 1 /* 06/VIII-2011 */
+ else if (p("--wcnf"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No problem output file specified\n");
+ return 1;
+ }
+ if (csa->out_cnf != NULL)
+ { xprintf("Only one output DIMACS CNF-SAT file allowed\n");
+ return 1;
+ }
+ csa->out_cnf = argv[k];
+ }
+#endif
+ else if (p("--log"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No log file specified\n");
+ return 1;
+ }
+ if (csa->log_file != NULL)
+ { xprintf("Only one log file allowed\n");
+ return 1;
+ }
+ csa->log_file = argv[k];
+ }
+ else if (p("-h") || p("--help"))
+ { print_help(argv[0]);
+ return -1;
+ }
+ else if (p("-v") || p("--version"))
+ { print_version(0);
+ return -1;
+ }
+#if 0 /* 08/III-2014 */
+ else if (p("--luf"))
+ csa->bfcp.type = GLP_BF_FT;
+ else if (p("--cbg"))
+ csa->bfcp.type = GLP_BF_BG;
+ else if (p("--cgr"))
+ csa->bfcp.type = GLP_BF_GR;
+#else
+ else if (p("--luf"))
+ { csa->bfcp.type &= 0x0F;
+ csa->bfcp.type |= GLP_BF_LUF;
+ }
+ else if (p("--btf"))
+ { csa->bfcp.type &= 0x0F;
+ csa->bfcp.type |= GLP_BF_BTF;
+ }
+ else if (p("--ft"))
+ { csa->bfcp.type &= 0xF0;
+ csa->bfcp.type |= GLP_BF_FT;
+ }
+ else if (p("--cbg"))
+ { csa->bfcp.type &= 0xF0;
+ csa->bfcp.type |= GLP_BF_BG;
+ }
+ else if (p("--cgr"))
+ { csa->bfcp.type &= 0xF0;
+ csa->bfcp.type |= GLP_BF_GR;
+ }
+#endif
+ else if (p("--primal"))
+ csa->smcp.meth = GLP_PRIMAL;
+ else if (p("--dual"))
+ csa->smcp.meth = GLP_DUAL;
+ else if (p("--std"))
+ csa->crash = USE_STD_BASIS;
+ else if (p("--adv"))
+ csa->crash = USE_ADV_BASIS;
+ else if (p("--bib"))
+ csa->crash = USE_CPX_BASIS;
+ else if (p("--ini"))
+ { csa->crash = USE_INI_BASIS;
+ csa->smcp.presolve = GLP_OFF;
+ k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No initial basis file specified\n");
+ return 1;
+ }
+ if (csa->ini_file != NULL)
+ { xprintf("Only one initial basis file allowed\n");
+ return 1;
+ }
+ csa->ini_file = argv[k];
+ }
+ else if (p("--steep"))
+ csa->smcp.pricing = GLP_PT_PSE;
+ else if (p("--nosteep"))
+ csa->smcp.pricing = GLP_PT_STD;
+ else if (p("--relax"))
+ csa->smcp.r_test = GLP_RT_HAR;
+ else if (p("--norelax"))
+ csa->smcp.r_test = GLP_RT_STD;
+#if 1 /* 28/III-2016 */
+ else if (p("--flip"))
+#if 0 /* 23/VI-2017 */
+ { csa->smcp.meth = GLP_DUAL;
+#else
+ /* now this option is implemented in both primal and dual */
+ {
+#endif
+ csa->smcp.r_test = GLP_RT_FLIP;
+ csa->iocp.flip = GLP_ON;
+ }
+#endif
+ else if (p("--presol"))
+ csa->smcp.presolve = GLP_ON;
+ else if (p("--nopresol"))
+ csa->smcp.presolve = GLP_OFF;
+ else if (p("--exact"))
+ csa->exact = 1;
+ else if (p("--xcheck"))
+ csa->xcheck = 1;
+ else if (p("--nord"))
+ csa->iptcp.ord_alg = GLP_ORD_NONE;
+ else if (p("--qmd"))
+ csa->iptcp.ord_alg = GLP_ORD_QMD;
+ else if (p("--amd"))
+ csa->iptcp.ord_alg = GLP_ORD_AMD;
+ else if (p("--symamd"))
+ csa->iptcp.ord_alg = GLP_ORD_SYMAMD;
+ else if (p("--nomip"))
+ csa->nomip = 1;
+ else if (p("--first"))
+ csa->iocp.br_tech = GLP_BR_FFV;
+ else if (p("--last"))
+ csa->iocp.br_tech = GLP_BR_LFV;
+ else if (p("--drtom"))
+ csa->iocp.br_tech = GLP_BR_DTH;
+ else if (p("--mostf"))
+ csa->iocp.br_tech = GLP_BR_MFV;
+ else if (p("--pcost"))
+ csa->iocp.br_tech = GLP_BR_PCH;
+ else if (p("--dfs"))
+ csa->iocp.bt_tech = GLP_BT_DFS;
+ else if (p("--bfs"))
+ csa->iocp.bt_tech = GLP_BT_BFS;
+ else if (p("--bestp"))
+ csa->iocp.bt_tech = GLP_BT_BPH;
+ else if (p("--bestb"))
+ csa->iocp.bt_tech = GLP_BT_BLB;
+ else if (p("--intopt"))
+ csa->iocp.presolve = GLP_ON;
+ else if (p("--nointopt"))
+ csa->iocp.presolve = GLP_OFF;
+ else if (p("--binarize"))
+ csa->iocp.presolve = csa->iocp.binarize = GLP_ON;
+ else if (p("--fpump"))
+ csa->iocp.fp_heur = GLP_ON;
+#if 1 /* 29/VI-2013 */
+ else if (p("--proxy"))
+ { csa->iocp.ps_heur = GLP_ON;
+ if (argv[k+1] && isdigit((unsigned char)argv[k+1][0]))
+ { int nnn;
+ k++;
+ if (str2int(argv[k], &nnn) || nnn < 1)
+ { xprintf("Invalid proxy time limit '%s'\n", argv[k]);
+ return 1;
+ }
+ csa->iocp.ps_tm_lim = 1000 * nnn;
+ }
+ }
+#endif
+ else if (p("--gomory"))
+ csa->iocp.gmi_cuts = GLP_ON;
+ else if (p("--mir"))
+ csa->iocp.mir_cuts = GLP_ON;
+ else if (p("--cover"))
+ csa->iocp.cov_cuts = GLP_ON;
+ else if (p("--clique"))
+ csa->iocp.clq_cuts = GLP_ON;
+ else if (p("--cuts"))
+ csa->iocp.gmi_cuts = csa->iocp.mir_cuts =
+ csa->iocp.cov_cuts = csa->iocp.clq_cuts = GLP_ON;
+ else if (p("--mipgap"))
+ { double mip_gap;
+ k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No relative gap tolerance specified\n");
+ return 1;
+ }
+ if (str2num(argv[k], &mip_gap) || mip_gap < 0.0)
+ { xprintf("Invalid relative mip gap tolerance '%s'\n",
+ argv[k]);
+ return 1;
+ }
+ csa->iocp.mip_gap = mip_gap;
+ }
+#if 1 /* 15/VIII-2011 */
+ else if (p("--minisat"))
+ csa->minisat = 1;
+ else if (p("--objbnd"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' ||
+ argv[k][0] == '-' && !isdigit((unsigned char)argv[k][1]))
+ { xprintf("No objective bound specified\n");
+ return 1;
+ }
+ csa->minisat = 1;
+ csa->use_bnd = 1;
+ if (str2int(argv[k], &csa->obj_bnd))
+ { xprintf("Invalid objective bound '%s' (should be integer"
+ " value)\n", argv[k]);
+ return 1;
+ }
+ }
+#endif
+#if 1 /* 11/VII-2013 */
+ else if (p("--use"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No input MIP solution file specified\n");
+ return 1;
+ }
+ if (csa->use_sol != NULL)
+ { xprintf("Only one input MIP solution file allowed\n");
+ return 1;
+ }
+ csa->use_sol = argv[k];
+ }
+ else if (p("--save"))
+ { k++;
+ if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-')
+ { xprintf("No output MIP solution file specified\n");
+ return 1;
+ }
+ if (csa->iocp.save_sol != NULL)
+ { xprintf("Only one output MIP solution file allowed\n");
+ return 1;
+ }
+ csa->iocp.save_sol = argv[k];
+ }
+#endif
+ else if (argv[k][0] == '-' ||
+ (argv[k][0] == '-' && argv[k][1] == '-'))
+ { xprintf("Invalid option '%s'; try %s --help\n",
+ argv[k], argv[0]);
+ return 1;
+ }
+ else
+ { if (csa->in_file != NULL)
+ { xprintf("Only one input problem file allowed\n");
+ return 1;
+ }
+ csa->in_file = argv[k];
+ }
+ }
+#undef p
+ return 0;
+}
+
+typedef struct { double rhs, pi; } v_data;
+typedef struct { double low, cap, cost, x; } a_data;
+
+#ifndef __WOE__
+int main(int argc, char *argv[])
+#else
+int __cdecl main(int argc, char *argv[])
+#endif
+{ /* stand-alone LP/MIP solver */
+ struct csa _csa, *csa = &_csa;
+ int ret;
+#if 0 /* 10/VI-2013 */
+ glp_long start;
+#else
+ double start;
+#endif
+ /* perform initialization */
+ csa->prob = glp_create_prob();
+ glp_get_bfcp(csa->prob, &csa->bfcp);
+ glp_init_smcp(&csa->smcp);
+ csa->smcp.presolve = GLP_ON;
+ glp_init_iptcp(&csa->iptcp);
+ glp_init_iocp(&csa->iocp);
+ csa->iocp.presolve = GLP_ON;
+ csa->tran = NULL;
+ csa->graph = NULL;
+ csa->format = FMT_MPS_FILE;
+ csa->in_file = NULL;
+ csa->ndf = 0;
+ csa->out_dpy = NULL;
+ csa->seed = 1;
+ csa->solution = SOL_BASIC;
+ csa->in_res = NULL;
+ csa->dir = 0;
+ csa->scale = 1;
+ csa->out_sol = NULL;
+ csa->out_res = NULL;
+ csa->out_ranges = NULL;
+ csa->check = 0;
+ csa->new_name = NULL;
+#if 1 /* 18/I-2018 */
+ csa->hide = 0;
+#endif
+ csa->out_mps = NULL;
+ csa->out_freemps = NULL;
+ csa->out_cpxlp = NULL;
+ csa->out_glp = NULL;
+#if 0
+ csa->out_pb = NULL;
+ csa->out_npb = NULL;
+#endif
+#if 1 /* 06/VIII-2011 */
+ csa->out_cnf = NULL;
+#endif
+ csa->log_file = NULL;
+ csa->crash = USE_ADV_BASIS;
+ csa->ini_file = NULL;
+ csa->exact = 0;
+ csa->xcheck = 0;
+ csa->nomip = 0;
+#if 1 /* 15/VIII-2011 */
+ csa->minisat = 0;
+ csa->use_bnd = 0;
+ csa->obj_bnd = 0;
+#endif
+#if 1 /* 11/VII-2013 */
+ csa->use_sol = NULL;
+#endif
+ /* parse command-line parameters */
+ ret = parse_cmdline(csa, argc, argv);
+ if (ret < 0)
+ { ret = EXIT_SUCCESS;
+ goto done;
+ }
+ if (ret > 0)
+ { ret = EXIT_FAILURE;
+ goto done;
+ }
+ /*--------------------------------------------------------------*/
+ /* remove all output files specified in the command line */
+ if (csa->out_dpy != NULL) remove(csa->out_dpy);
+ if (csa->out_sol != NULL) remove(csa->out_sol);
+ if (csa->out_res != NULL) remove(csa->out_res);
+ if (csa->out_ranges != NULL) remove(csa->out_ranges);
+ if (csa->out_mps != NULL) remove(csa->out_mps);
+ if (csa->out_freemps != NULL) remove(csa->out_freemps);
+ if (csa->out_cpxlp != NULL) remove(csa->out_cpxlp);
+ if (csa->out_glp != NULL) remove(csa->out_glp);
+#if 0
+ if (csa->out_pb != NULL) remove(csa->out_pb);
+ if (csa->out_npb != NULL) remove(csa->out_npb);
+#endif
+#if 1 /* 06/VIII-2011 */
+ if (csa->out_cnf != NULL) remove(csa->out_cnf);
+#endif
+ if (csa->log_file != NULL) remove(csa->log_file);
+ /*--------------------------------------------------------------*/
+ /* open log file, if required */
+ if (csa->log_file != NULL)
+ { if (glp_open_tee(csa->log_file))
+ { xprintf("Unable to create log file\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /*--------------------------------------------------------------*/
+ /* print version information */
+ print_version(1);
+ /*--------------------------------------------------------------*/
+ /* print parameters specified in the command line */
+ if (argc > 1)
+ { int k, len = INT_MAX;
+ xprintf("Parameter(s) specified in the command line:");
+ for (k = 1; k < argc; k++)
+ { if (len > 72)
+ xprintf("\n"), len = 0;
+ xprintf(" %s", argv[k]);
+ len += 1 + strlen(argv[k]);
+ }
+ xprintf("\n");
+ }
+ /*--------------------------------------------------------------*/
+ /* read problem data from the input file */
+ if (csa->in_file == NULL)
+ { xprintf("No input problem file specified; try %s --help\n",
+ argv[0]);
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ if (csa->format == FMT_MPS_DECK)
+ { ret = glp_read_mps(csa->prob, GLP_MPS_DECK, NULL,
+ csa->in_file);
+ if (ret != 0)
+err1: { xprintf("MPS file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ else if (csa->format == FMT_MPS_FILE)
+ { ret = glp_read_mps(csa->prob, GLP_MPS_FILE, NULL,
+ csa->in_file);
+ if (ret != 0) goto err1;
+ }
+ else if (csa->format == FMT_LP)
+ { ret = glp_read_lp(csa->prob, NULL, csa->in_file);
+ if (ret != 0)
+ { xprintf("CPLEX LP file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ else if (csa->format == FMT_GLP)
+ { ret = glp_read_prob(csa->prob, 0, csa->in_file);
+ if (ret != 0)
+ { xprintf("GLPK LP/MIP file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ else if (csa->format == FMT_MATHPROG)
+ { int k;
+ /* allocate the translator workspace */
+ csa->tran = glp_mpl_alloc_wksp();
+ /* set seed value */
+ if (csa->seed == 0x80000000)
+#if 0 /* 10/VI-2013 */
+ { csa->seed = glp_time().lo;
+#else
+ { csa->seed = (int)fmod(glp_time(), 1000000000.0);
+#endif
+ xprintf("Seed value %d will be used\n", csa->seed);
+ }
+ glp_mpl_init_rand(csa->tran, csa->seed);
+ /* read model section and optional data section */
+ if (glp_mpl_read_model(csa->tran, csa->in_file, csa->ndf > 0))
+err2: { xprintf("MathProg model processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ /* read optional data section(s), if necessary */
+ for (k = 1; k <= csa->ndf; k++)
+ { if (glp_mpl_read_data(csa->tran, csa->in_data[k]))
+ goto err2;
+ }
+ /* generate the model */
+ if (glp_mpl_generate(csa->tran, csa->out_dpy)) goto err2;
+ /* build the problem instance from the model */
+ glp_mpl_build_prob(csa->tran, csa->prob);
+ }
+ else if (csa->format == FMT_MIN_COST)
+ { csa->graph = glp_create_graph(sizeof(v_data), sizeof(a_data));
+ ret = glp_read_mincost(csa->graph, offsetof(v_data, rhs),
+ offsetof(a_data, low), offsetof(a_data, cap),
+ offsetof(a_data, cost), csa->in_file);
+ if (ret != 0)
+ { xprintf("DIMACS file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ glp_mincost_lp(csa->prob, csa->graph, GLP_ON,
+ offsetof(v_data, rhs), offsetof(a_data, low),
+ offsetof(a_data, cap), offsetof(a_data, cost));
+ glp_set_prob_name(csa->prob, csa->in_file);
+ }
+ else if (csa->format == FMT_MAX_FLOW)
+ { int s, t;
+ csa->graph = glp_create_graph(sizeof(v_data), sizeof(a_data));
+ ret = glp_read_maxflow(csa->graph, &s, &t,
+ offsetof(a_data, cap), csa->in_file);
+ if (ret != 0)
+ { xprintf("DIMACS file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ glp_maxflow_lp(csa->prob, csa->graph, GLP_ON, s, t,
+ offsetof(a_data, cap));
+ glp_set_prob_name(csa->prob, csa->in_file);
+ }
+#if 1 /* 06/VIII-2011 */
+ else if (csa->format == FMT_CNF)
+ { ret = glp_read_cnfsat(csa->prob, csa->in_file);
+ if (ret != 0)
+ { xprintf("DIMACS file processing error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ glp_set_prob_name(csa->prob, csa->in_file);
+ }
+#endif
+ else
+ xassert(csa != csa);
+ /*--------------------------------------------------------------*/
+ /* change problem name, if required */
+ if (csa->new_name != NULL)
+ glp_set_prob_name(csa->prob, csa->new_name);
+ /* change optimization direction, if required */
+ if (csa->dir != 0)
+ glp_set_obj_dir(csa->prob, csa->dir);
+ /* sort elements of the constraint matrix */
+ glp_sort_matrix(csa->prob);
+#if 1 /* 18/I-2018 */
+ /*--------------------------------------------------------------*/
+ /* remove all symbolic names from problem object, if required */
+ if (csa->hide)
+ { int i, j;
+ glp_set_obj_name(csa->prob, NULL);
+ glp_delete_index(csa->prob);
+ for (i = glp_get_num_rows(csa->prob); i >= 1; i--)
+ glp_set_row_name(csa->prob, i, NULL);
+ for (j = glp_get_num_cols(csa->prob); j >= 1; j--)
+ glp_set_col_name(csa->prob, j, NULL);
+ }
+#endif
+ /*--------------------------------------------------------------*/
+ /* write problem data in fixed MPS format, if required */
+ if (csa->out_mps != NULL)
+ { ret = glp_write_mps(csa->prob, GLP_MPS_DECK, NULL,
+ csa->out_mps);
+ if (ret != 0)
+ { xprintf("Unable to write problem in fixed MPS format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write problem data in free MPS format, if required */
+ if (csa->out_freemps != NULL)
+ { ret = glp_write_mps(csa->prob, GLP_MPS_FILE, NULL,
+ csa->out_freemps);
+ if (ret != 0)
+ { xprintf("Unable to write problem in free MPS format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write problem data in CPLEX LP format, if required */
+ if (csa->out_cpxlp != NULL)
+ { ret = glp_write_lp(csa->prob, NULL, csa->out_cpxlp);
+ if (ret != 0)
+ { xprintf("Unable to write problem in CPLEX LP format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write problem data in GLPK format, if required */
+ if (csa->out_glp != NULL)
+ { ret = glp_write_prob(csa->prob, 0, csa->out_glp);
+ if (ret != 0)
+ { xprintf("Unable to write problem in GLPK format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+#if 0
+ /* write problem data in OPB format, if required */
+ if (csa->out_pb != NULL)
+ { ret = lpx_write_pb(csa->prob, csa->out_pb, 0, 0);
+ if (ret != 0)
+ { xprintf("Unable to write problem in OPB format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write problem data in normalized OPB format, if required */
+ if (csa->out_npb != NULL)
+ { ret = lpx_write_pb(csa->prob, csa->out_npb, 1, 1);
+ if (ret != 0)
+ { xprintf(
+ "Unable to write problem in normalized OPB format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+#endif
+#if 1 /* 06/VIII-2011 */
+ /* write problem data in DIMACS CNF-SAT format, if required */
+ if (csa->out_cnf != NULL)
+ { ret = glp_write_cnfsat(csa->prob, csa->out_cnf);
+ if (ret != 0)
+ { xprintf(
+ "Unable to write problem in DIMACS CNF-SAT format\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+#endif
+ /*--------------------------------------------------------------*/
+ /* if only problem data check is required, skip computations */
+ if (csa->check)
+ {
+#if 1 /* 29/III-2016 */
+ /* report problem characteristics */
+ int j, cnt = 0;
+ xprintf("--- Problem Characteristics ---\n");
+ xprintf("Number of rows = %8d\n",
+ glp_get_num_rows(csa->prob));
+ xprintf("Number of columns = %8d\n",
+ glp_get_num_cols(csa->prob));
+ xprintf("Number of non-zeros (matrix) = %8d\n",
+ glp_get_num_nz(csa->prob));
+ for (j = glp_get_num_cols(csa->prob); j >= 1; j--)
+ { if (glp_get_obj_coef(csa->prob, j) != 0.0)
+ cnt++;
+ }
+ xprintf("Number of non-zeros (objrow) = %8d\n",
+ cnt);
+#endif
+ ret = EXIT_SUCCESS;
+ goto done;
+ }
+ /*--------------------------------------------------------------*/
+ /* determine the solution type */
+ if (!csa->nomip &&
+ glp_get_num_int(csa->prob) + glp_get_num_bin(csa->prob) > 0)
+ { if (csa->solution == SOL_INTERIOR)
+ { xprintf("Interior-point method is not able to solve MIP pro"
+ "blem; use --simplex\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ csa->solution = SOL_INTEGER;
+ }
+ /*--------------------------------------------------------------*/
+ /* if solution is provided, read it and skip computations */
+ if (csa->in_res != NULL)
+ { if (csa->solution == SOL_BASIC)
+ ret = glp_read_sol(csa->prob, csa->in_res);
+ else if (csa->solution == SOL_INTERIOR)
+ ret = glp_read_ipt(csa->prob, csa->in_res);
+ else if (csa->solution == SOL_INTEGER)
+ ret = glp_read_mip(csa->prob, csa->in_res);
+ else
+ xassert(csa != csa);
+ if (ret != 0)
+ { xprintf("Unable to read problem solution\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ goto skip;
+ }
+#if 1 /* 11/VII-2013 */
+ /*--------------------------------------------------------------*/
+ /* if initial MIP solution is provided, read it */
+ if (csa->solution == SOL_INTEGER && csa->use_sol != NULL)
+ { ret = glp_read_mip(csa->prob, csa->use_sol);
+ if (ret != 0)
+ { xprintf("Unable to read initial MIP solution\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ csa->iocp.use_sol = GLP_ON;
+ }
+#endif
+ /*--------------------------------------------------------------*/
+ /* scale the problem data, if required */
+ if (csa->scale)
+ { if (csa->solution == SOL_BASIC && !csa->smcp.presolve ||
+ csa->solution == SOL_INTERIOR ||
+ csa->solution == SOL_INTEGER && !csa->iocp.presolve)
+ glp_scale_prob(csa->prob, GLP_SF_AUTO);
+ }
+ /*--------------------------------------------------------------*/
+ /* construct starting LP basis */
+ if (csa->solution == SOL_BASIC && !csa->smcp.presolve ||
+ csa->solution == SOL_INTEGER && !csa->iocp.presolve)
+ { if (csa->crash == USE_STD_BASIS)
+ glp_std_basis(csa->prob);
+ else if (csa->crash == USE_ADV_BASIS)
+ glp_adv_basis(csa->prob, 0);
+ else if (csa->crash == USE_CPX_BASIS)
+ glp_cpx_basis(csa->prob);
+ else if (csa->crash == USE_INI_BASIS)
+ { ret = glp_read_sol(csa->prob, csa->ini_file);
+ if (ret != 0)
+ { xprintf("Unable to read initial basis\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ else
+ xassert(csa != csa);
+ }
+ /*--------------------------------------------------------------*/
+ /* solve the problem */
+
+ start = glp_time();
+#ifdef VERIMAG
+ clock_prepare();
+ clock_start();
+#endif
+ if (csa->solution == SOL_BASIC)
+ { if (!csa->exact)
+ { glp_set_bfcp(csa->prob, &csa->bfcp);
+ glp_simplex(csa->prob, &csa->smcp);
+ if (csa->xcheck)
+ { if (csa->smcp.presolve &&
+ glp_get_status(csa->prob) != GLP_OPT)
+ xprintf("If you need to check final basis for non-opt"
+ "imal solution, use --nopresol\n");
+ else
+ glp_exact(csa->prob, &csa->smcp);
+ }
+ if (csa->out_sol != NULL || csa->out_res != NULL)
+ { if (csa->smcp.presolve &&
+ glp_get_status(csa->prob) != GLP_OPT)
+ xprintf("If you need actual output for non-optimal solut"
+ "ion, use --nopresol\n");
+ }
+ }
+ else
+ glp_exact(csa->prob, &csa->smcp);
+ }
+ else if (csa->solution == SOL_INTERIOR)
+ glp_interior(csa->prob, &csa->iptcp);
+#if 1 /* 15/VIII-2011 */
+ else if (csa->solution == SOL_INTEGER && csa->minisat)
+ { if (glp_check_cnfsat(csa->prob) == 0)
+ glp_minisat1(csa->prob);
+ else
+ glp_intfeas1(csa->prob, csa->use_bnd, csa->obj_bnd);
+ }
+#endif
+ else if (csa->solution == SOL_INTEGER)
+ { glp_set_bfcp(csa->prob, &csa->bfcp);
+ if (!csa->iocp.presolve)
+ glp_simplex(csa->prob, &csa->smcp);
+#if 0
+ csa->iocp.msg_lev = GLP_MSG_DBG;
+ csa->iocp.pp_tech = GLP_PP_NONE;
+#endif
+#ifdef GLP_CB_FUNC /* 05/IV-2016 */
+ { extern void GLP_CB_FUNC(glp_tree *, void *);
+ csa->iocp.cb_func = GLP_CB_FUNC;
+ csa->iocp.cb_info = NULL;
+ }
+#endif
+ glp_intopt(csa->prob, &csa->iocp);
+ }
+ else
+ xassert(csa != csa);
+ /*--------------------------------------------------------------*/
+ /* display statistics */
+#ifdef VERIMAG
+ clock_stop();
+ print_total_clock();
+#endif
+ xprintf("Time used: %.1f secs\n", glp_difftime(glp_time(),
+ start));
+#if 0 /* 16/II-2012 */
+ { glp_long tpeak;
+ char buf[50];
+ glp_mem_usage(NULL, NULL, NULL, &tpeak);
+ xprintf("Memory used: %.1f Mb (%s bytes)\n",
+ xltod(tpeak) / 1048576.0, xltoa(tpeak, buf));
+ }
+#else
+ { size_t tpeak;
+ glp_mem_usage(NULL, NULL, NULL, &tpeak);
+ xprintf("Memory used: %.1f Mb (%.0f bytes)\n",
+ (double)tpeak / 1048576.0, (double)tpeak);
+ }
+#endif
+ /*--------------------------------------------------------------*/
+skip: /* postsolve the model, if necessary */
+ if (csa->tran != NULL)
+ { if (csa->solution == SOL_BASIC)
+ { if (!(glp_get_status(csa->prob) == GLP_OPT ||
+ glp_get_status(csa->prob) == GLP_FEAS))
+ ret = -1;
+ else
+ ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_SOL);
+ }
+ else if (csa->solution == SOL_INTERIOR)
+ { if (!(glp_ipt_status(csa->prob) == GLP_OPT ||
+ glp_ipt_status(csa->prob) == GLP_FEAS))
+ ret = -1;
+ else
+ ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_IPT);
+ }
+ else if (csa->solution == SOL_INTEGER)
+ { if (!(glp_mip_status(csa->prob) == GLP_OPT ||
+ glp_mip_status(csa->prob) == GLP_FEAS))
+ ret = -1;
+ else
+ ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_MIP);
+ }
+ else
+ xassert(csa != csa);
+ if (ret > 0)
+ { xprintf("Model postsolving error\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /*--------------------------------------------------------------*/
+ /* write problem solution in printable format, if required */
+ if (csa->out_sol != NULL)
+ { if (csa->solution == SOL_BASIC)
+ ret = glp_print_sol(csa->prob, csa->out_sol);
+ else if (csa->solution == SOL_INTERIOR)
+ ret = glp_print_ipt(csa->prob, csa->out_sol);
+ else if (csa->solution == SOL_INTEGER)
+ ret = glp_print_mip(csa->prob, csa->out_sol);
+ else
+ xassert(csa != csa);
+ if (ret != 0)
+ { xprintf("Unable to write problem solution\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write problem solution in printable format, if required */
+ if (csa->out_res != NULL)
+ { if (csa->solution == SOL_BASIC)
+ ret = glp_write_sol(csa->prob, csa->out_res);
+ else if (csa->solution == SOL_INTERIOR)
+ ret = glp_write_ipt(csa->prob, csa->out_res);
+ else if (csa->solution == SOL_INTEGER)
+ ret = glp_write_mip(csa->prob, csa->out_res);
+ else
+ xassert(csa != csa);
+ if (ret != 0)
+ { xprintf("Unable to write problem solution\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ /* write sensitivity analysis report, if required */
+ if (csa->out_ranges != NULL)
+ { if (csa->solution == SOL_BASIC)
+ { if (glp_get_status(csa->prob) == GLP_OPT)
+ { if (glp_bf_exists(csa->prob))
+ranges: { ret = glp_print_ranges(csa->prob, 0, NULL, 0,
+ csa->out_ranges);
+ if (ret != 0)
+ { xprintf("Unable to write sensitivity analysis repo"
+ "rt\n");
+ ret = EXIT_FAILURE;
+ goto done;
+ }
+ }
+ else
+ { ret = glp_factorize(csa->prob);
+ if (ret == 0) goto ranges;
+ xprintf("Cannot produce sensitivity analysis report d"
+ "ue to error in basis factorization (glp_factorize"
+ " returned %d); try --nopresol\n", ret);
+ }
+ }
+ else
+ xprintf("Cannot produce sensitivity analysis report for "
+ "non-optimal basic solution\n");
+ }
+ else
+ xprintf("Cannot produce sensitivity analysis report for int"
+ "erior-point or MIP solution\n");
+ }
+ /*--------------------------------------------------------------*/
+ /* all seems to be ok */
+ ret = EXIT_SUCCESS;
+ /*--------------------------------------------------------------*/
+done: /* delete the LP/MIP problem object */
+ if (csa->prob != NULL)
+ glp_delete_prob(csa->prob);
+ /* free the translator workspace, if necessary */
+ if (csa->tran != NULL)
+ glp_mpl_free_wksp(csa->tran);
+ /* delete the network problem object, if necessary */
+ if (csa->graph != NULL)
+ glp_delete_graph(csa->graph);
+#if 0 /* 23/XI-2015 */
+ xassert(gmp_pool_count() == 0);
+ gmp_free_mem();
+#endif
+ /* close log file, if necessary */
+ if (csa->log_file != NULL) glp_close_tee();
+ /* check that no memory blocks are still allocated */
+#if 0 /* 16/II-2012 */
+ { int count;
+ glp_long total;
+ glp_mem_usage(&count, NULL, &total, NULL);
+ if (count != 0)
+ xerror("Error: %d memory block(s) were lost\n", count);
+ xassert(count == 0);
+ xassert(total.lo == 0 && total.hi == 0);
+ }
+#else
+ { int count;
+ size_t total;
+ glp_mem_usage(&count, NULL, &total, NULL);
+ if (count != 0)
+ xerror("Error: %d memory block(s) were lost\n", count);
+ xassert(total == 0);
+ }
+#endif
+ /* free the GLPK environment */
+ glp_free_env();
+ /* return to the control program */
+ return ret;
+}
+
+/* eof */
diff --git a/test/monniaux/glpk-4.65/examples/prod.mod b/test/monniaux/glpk-4.65/examples/prod.mod
new file mode 100644
index 00000000..aa793f76
--- /dev/null
+++ b/test/monniaux/glpk-4.65/examples/prod.mod
@@ -0,0 +1,331 @@
+# PROD, a multiperiod production model
+#
+# References:
+# Robert Fourer, David M. Gay and Brian W. Kernighan, "A Modeling Language
+# for Mathematical Programming." Management Science 36 (1990) 519-554.
+
+### PRODUCTION SETS AND PARAMETERS ###
+
+set prd 'products'; # Members of the product group
+
+param pt 'production time' {prd} > 0;
+
+ # Crew-hours to produce 1000 units
+
+param pc 'production cost' {prd} > 0;
+
+ # Nominal production cost per 1000, used
+ # to compute inventory and shortage costs
+
+### TIME PERIOD SETS AND PARAMETERS ###
+
+param first > 0 integer;
+ # Index of first production period to be modeled
+
+param last > first integer;
+
+ # Index of last production period to be modeled
+
+set time 'planning horizon' := first..last;
+
+### EMPLOYMENT PARAMETERS ###
+
+param cs 'crew size' > 0 integer;
+
+ # Workers per crew
+
+param sl 'shift length' > 0;
+
+ # Regular-time hours per shift
+
+param rtr 'regular time rate' > 0;
+
+ # Wage per hour for regular-time labor
+
+param otr 'overtime rate' > rtr;
+
+ # Wage per hour for overtime labor
+
+param iw 'initial workforce' >= 0 integer;
+
+ # Crews employed at start of first period
+
+param dpp 'days per period' {time} > 0;
+
+ # Regular working days in a production period
+
+param ol 'overtime limit' {time} >= 0;
+
+ # Maximum crew-hours of overtime in a period
+
+param cmin 'crew minimum' {time} >= 0;
+
+ # Lower limit on average employment in a period
+
+param cmax 'crew maximum' {t in time} >= cmin[t];
+
+ # Upper limit on average employment in a period
+
+param hc 'hiring cost' {time} >= 0;
+
+ # Penalty cost of hiring a crew
+
+param lc 'layoff cost' {time} >= 0;
+
+ # Penalty cost of laying off a crew
+
+### DEMAND PARAMETERS ###
+
+param dem 'demand' {prd,first..last+1} >= 0;
+
+ # Requirements (in 1000s)
+ # to be met from current production and inventory
+
+param pro 'promoted' {prd,first..last+1} logical;
+
+ # true if product will be the subject
+ # of a special promotion in the period
+
+### INVENTORY AND SHORTAGE PARAMETERS ###
+
+param rir 'regular inventory ratio' >= 0;
+
+ # Proportion of non-promoted demand
+ # that must be in inventory the previous period
+
+param pir 'promotional inventory ratio' >= 0;
+
+ # Proportion of promoted demand
+ # that must be in inventory the previous period
+
+param life 'inventory lifetime' > 0 integer;
+
+ # Upper limit on number of periods that
+ # any product may sit in inventory
+
+param cri 'inventory cost ratio' {prd} > 0;
+
+ # Inventory cost per 1000 units is
+ # cri times nominal production cost
+
+param crs 'shortage cost ratio' {prd} > 0;
+
+ # Shortage cost per 1000 units is
+ # crs times nominal production cost
+
+param iinv 'initial inventory' {prd} >= 0;
+
+ # Inventory at start of first period; age unknown
+
+param iil 'initial inventory left' {p in prd, t in time}
+ := iinv[p] less sum {v in first..t} dem[p,v];
+
+ # Initial inventory still available for allocation
+ # at end of period t
+
+param minv 'minimum inventory' {p in prd, t in time}
+ := dem[p,t+1] * (if pro[p,t+1] then pir else rir);
+
+ # Lower limit on inventory at end of period t
+
+### VARIABLES ###
+
+var Crews{first-1..last} >= 0;
+
+ # Average number of crews employed in each period
+
+var Hire{time} >= 0; # Crews hired from previous to current period
+
+var Layoff{time} >= 0; # Crews laid off from previous to current period
+
+var Rprd 'regular production' {prd,time} >= 0;
+
+ # Production using regular-time labor, in 1000s
+
+var Oprd 'overtime production' {prd,time} >= 0;
+
+ # Production using overtime labor, in 1000s
+
+var Inv 'inventory' {prd,time,1..life} >= 0;
+
+ # Inv[p,t,a] is the amount of product p that is
+ # a periods old -- produced in period (t+1)-a --
+ # and still in storage at the end of period t
+
+var Short 'shortage' {prd,time} >= 0;
+
+ # Accumulated unsatisfied demand at the end of period t
+
+### OBJECTIVE ###
+
+minimize cost:
+
+ sum {t in time} rtr * sl * dpp[t] * cs * Crews[t] +
+ sum {t in time} hc[t] * Hire[t] +
+ sum {t in time} lc[t] * Layoff[t] +
+ sum {t in time, p in prd} otr * cs * pt[p] * Oprd[p,t] +
+ sum {t in time, p in prd, a in 1..life} cri[p] * pc[p] * Inv[p,t,a] +
+ sum {t in time, p in prd} crs[p] * pc[p] * Short[p,t];
+
+ # Full regular wages for all crews employed, plus
+ # penalties for hiring and layoffs, plus
+ # wages for any overtime worked, plus
+ # inventory and shortage costs
+
+ # (All other production costs are assumed
+ # to depend on initial inventory and on demands,
+ # and so are not included explicitly.)
+
+### CONSTRAINTS ###
+
+rlim 'regular-time limit' {t in time}:
+
+ sum {p in prd} pt[p] * Rprd[p,t] <= sl * dpp[t] * Crews[t];
+
+ # Hours needed to accomplish all regular-time
+ # production in a period must not exceed
+ # hours available on all shifts
+
+olim 'overtime limit' {t in time}:
+
+ sum {p in prd} pt[p] * Oprd[p,t] <= ol[t];
+
+ # Hours needed to accomplish all overtime
+ # production in a period must not exceed
+ # the specified overtime limit
+
+empl0 'initial crew level': Crews[first-1] = iw;
+
+ # Use given initial workforce
+
+empl 'crew levels' {t in time}: Crews[t] = Crews[t-1] + Hire[t] - Layoff[t];
+
+ # Workforce changes by hiring or layoffs
+
+emplbnd 'crew limits' {t in time}: cmin[t] <= Crews[t] <= cmax[t];
+
+ # Workforce must remain within specified bounds
+
+dreq1 'first demand requirement' {p in prd}:
+
+ Rprd[p,first] + Oprd[p,first] + Short[p,first]
+ - Inv[p,first,1] = dem[p,first] less iinv[p];
+
+dreq 'demand requirements' {p in prd, t in first+1..last}:
+
+ Rprd[p,t] + Oprd[p,t] + Short[p,t] - Short[p,t-1]
+ + sum {a in 1..life} (Inv[p,t-1,a] - Inv[p,t,a])
+ = dem[p,t] less iil[p,t-1];
+
+ # Production plus increase in shortage plus
+ # decrease in inventory must equal demand
+
+ireq 'inventory requirements' {p in prd, t in time}:
+
+ sum {a in 1..life} Inv[p,t,a] + iil[p,t] >= minv[p,t];
+
+ # Inventory in storage at end of period t
+ # must meet specified minimum
+
+izero 'impossible inventories' {p in prd, v in 1..life-1, a in v+1..life}:
+
+ Inv[p,first+v-1,a] = 0;
+
+ # In the vth period (starting from first)
+ # no inventory may be more than v periods old
+ # (initial inventories are handled separately)
+
+ilim1 'new-inventory limits' {p in prd, t in time}:
+
+ Inv[p,t,1] <= Rprd[p,t] + Oprd[p,t];
+
+ # New inventory cannot exceed
+ # production in the most recent period
+
+ilim 'inventory limits' {p in prd, t in first+1..last, a in 2..life}:
+
+ Inv[p,t,a] <= Inv[p,t-1,a-1];
+
+ # Inventory left from period (t+1)-p
+ # can only decrease as time goes on
+
+### DATA ###
+
+data;
+
+set prd := 18REG 24REG 24PRO ;
+
+param first := 1 ;
+param last := 13 ;
+param life := 2 ;
+
+param cs := 18 ;
+param sl := 8 ;
+param iw := 8 ;
+
+param rtr := 16.00 ;
+param otr := 43.85 ;
+param rir := 0.75 ;
+param pir := 0.80 ;
+
+param : pt pc cri crs iinv :=
+
+ 18REG 1.194 2304. 0.015 1.100 82.0
+ 24REG 1.509 2920. 0.015 1.100 792.2
+ 24PRO 1.509 2910. 0.015 1.100 0.0 ;
+
+param : dpp ol cmin cmax hc lc :=
+
+ 1 19.5 96.0 0.0 8.0 7500 7500
+ 2 19.0 96.0 0.0 8.0 7500 7500
+ 3 20.0 96.0 0.0 8.0 7500 7500
+ 4 19.0 96.0 0.0 8.0 7500 7500
+ 5 19.5 96.0 0.0 8.0 15000 15000
+ 6 19.0 96.0 0.0 8.0 15000 15000
+ 7 19.0 96.0 0.0 8.0 15000 15000
+ 8 20.0 96.0 0.0 8.0 15000 15000
+ 9 19.0 96.0 0.0 8.0 15000 15000
+ 10 20.0 96.0 0.0 8.0 15000 15000
+ 11 20.0 96.0 0.0 8.0 7500 7500
+ 12 18.0 96.0 0.0 8.0 7500 7500
+ 13 18.0 96.0 0.0 8.0 7500 7500 ;
+
+param dem (tr) :
+
+ 18REG 24REG 24PRO :=
+
+ 1 63.8 1212.0 0.0
+ 2 76.0 306.2 0.0
+ 3 88.4 319.0 0.0
+ 4 913.8 208.4 0.0
+ 5 115.0 298.0 0.0
+ 6 133.8 328.2 0.0
+ 7 79.6 959.6 0.0
+ 8 111.0 257.6 0.0
+ 9 121.6 335.6 0.0
+ 10 470.0 118.0 1102.0
+ 11 78.4 284.8 0.0
+ 12 99.4 970.0 0.0
+ 13 140.4 343.8 0.0
+ 14 63.8 1212.0 0.0 ;
+
+param pro (tr) :
+
+ 18REG 24REG 24PRO :=
+
+ 1 0 1 0
+ 2 0 0 0
+ 3 0 0 0
+ 4 1 0 0
+ 5 0 0 0
+ 6 0 0 0
+ 7 0 1 0
+ 8 0 0 0
+ 9 0 0 0
+ 10 1 0 1
+ 11 0 0 0
+ 12 0 0 0
+ 13 0 1 0
+ 14 0 1 0 ;
+
+end;