aboutsummaryrefslogtreecommitdiff
path: root/src/ats
diff options
context:
space:
mode:
authorMatthias Wachs <wachs@net.in.tum.de>2014-05-13 21:54:23 +0000
committerMatthias Wachs <wachs@net.in.tum.de>2014-05-13 21:54:23 +0000
commit748449cc89a8ef631b8c3c5c3b9168634fc355a5 (patch)
tree7a7e444e78d19c51408320611ef81215b33bed3c /src/ats
parent0dcd9e8e86aa2260b00d823a5fda87f9a18bdad1 (diff)
downloadgnunet-748449cc89a8ef631b8c3c5c3b9168634fc355a5.tar.gz
gnunet-748449cc89a8ef631b8c3c5c3b9168634fc355a5.zip
implementation of mip gap tolerance interval
Diffstat (limited to 'src/ats')
-rw-r--r--src/ats/ats.conf.in6
-rw-r--r--src/ats/perf_ats_solver.c2
-rw-r--r--src/ats/perf_ats_solver.conf13
-rw-r--r--src/ats/plugin_ats_mlp.c192
-rw-r--r--src/ats/plugin_ats_mlp.h7
5 files changed, 163 insertions, 57 deletions
diff --git a/src/ats/ats.conf.in b/src/ats/ats.conf.in
index db70f143a..e1ad75c8f 100644
--- a/src/ats/ats.conf.in
+++ b/src/ats/ats.conf.in
@@ -44,8 +44,12 @@ PROP_STABILITY_FACTOR = 125
44# MLP specific settings 44# MLP specific settings
45# MLP defaults 45# MLP defaults
46 46
47# Maximum duration for a solution process 47# Maximum duration for a solution process (both LP and MILP)
48# MLP_MAX_DURATION = 3 s 48# MLP_MAX_DURATION = 3 s
49# Maximum numbero of iterations for a solution process (only LP)
50# MLP_MAX_ITERATIONS =
51# Tolerated MIP Gap in percent [0 .. 100]
52# MLP_MAX_MIP_GAP = 0.0
49 53
50# Maximum number of iterations for a solution process 54# Maximum number of iterations for a solution process
51# MLP_MAX_ITERATIONS = 1024 55# MLP_MAX_ITERATIONS = 1024
diff --git a/src/ats/perf_ats_solver.c b/src/ats/perf_ats_solver.c
index 2017b794b..01906c87d 100644
--- a/src/ats/perf_ats_solver.c
+++ b/src/ats/perf_ats_solver.c
@@ -27,7 +27,7 @@
27#include "gnunet_util_lib.h" 27#include "gnunet_util_lib.h"
28#include "gnunet_statistics_service.h" 28#include "gnunet_statistics_service.h"
29#include "gnunet-service-ats_addresses.h" 29#include "gnunet-service-ats_addresses.h"
30#include "gnunet-service-ats_normalization.h" 30
31#include "gnunet_ats_service.h" 31#include "gnunet_ats_service.h"
32#include "gnunet_ats_plugin.h" 32#include "gnunet_ats_plugin.h"
33#include "test_ats_api_common.h" 33#include "test_ats_api_common.h"
diff --git a/src/ats/perf_ats_solver.conf b/src/ats/perf_ats_solver.conf
index 7de6d5d00..0557203f4 100644
--- a/src/ats/perf_ats_solver.conf
+++ b/src/ats/perf_ats_solver.conf
@@ -35,6 +35,9 @@ PROP_STABILITY_FACTOR = 125
35 35
36# Maximum number of iterations for a solution process 36# Maximum number of iterations for a solution process
37# MLP_MAX_ITERATIONS = 1024 37# MLP_MAX_ITERATIONS = 1024
38# Tolerated MIP Gap [0.0 .. 1.0]
39MLP_MAX_MIP_GAP = 0,025
40
38# MLP_COEFFICIENT_D = 1.0 41# MLP_COEFFICIENT_D = 1.0
39# MLP_COEFFICIENT_U = 1.0 42# MLP_COEFFICIENT_U = 1.0
40# MLP_COEFFICIENT_R = 1.0 43# MLP_COEFFICIENT_R = 1.0
@@ -43,7 +46,8 @@ MLP_MIN_BANDWIDTH = 10
43# MLP_DBG_FEASIBILITY_ONLY = YES 46# MLP_DBG_FEASIBILITY_ONLY = YES
44MLP_DBG_AUTOSCALE_PROBLEM = YES 47MLP_DBG_AUTOSCALE_PROBLEM = YES
45# MLP_DBG_INTOPT_PRESOLVE = YES 48# MLP_DBG_INTOPT_PRESOLVE = YES
46 49# Print GLPK output
50#MLP_DBG_GLPK_VERBOSE = YES
47 51
48#MLP_DBG_OPTIMIZE_UTILITY = NO 52#MLP_DBG_OPTIMIZE_UTILITY = NO
49#MLP_DBG_OPTIMIZE_QUALITY = NO 53#MLP_DBG_OPTIMIZE_QUALITY = NO
@@ -54,8 +58,7 @@ MLP_LOG_FORMAT = CPLEX
54 58
55# MLP Log settings 59# MLP Log settings
56# Dump all problems to disk 60# Dump all problems to disk
57MLP_DUMP_PROBLEM_ALL = YES 61# MLP_DUMP_PROBLEM_ALL = YES
58# Dump all solution to disk 62# Dump all solution to disk
59MLP_DUMP_SOLUTION_ALL = YES 63# MLP_DUMP_SOLUTION_ALL = YES
60# Print GLPK output 64
61MLP_DBG_GLPK_VERBOSE = NO
diff --git a/src/ats/plugin_ats_mlp.c b/src/ats/plugin_ats_mlp.c
index 385b14a16..c4c97b796 100644
--- a/src/ats/plugin_ats_mlp.c
+++ b/src/ats/plugin_ats_mlp.c
@@ -147,8 +147,9 @@
147static int 147static int
148mlp_term_hook (void *info, const char *s) 148mlp_term_hook (void *info, const char *s)
149{ 149{
150 /* Not needed atm struct MLP_information *mlp = info; */ 150 struct GAS_MLP_Handle *mlp = info;
151 LOG (GNUNET_ERROR_TYPE_ERROR, "%s", s); 151 if (mlp->opt_dbg_glpk_verbose)
152 LOG (GNUNET_ERROR_TYPE_ERROR, "%s", s);
152 return 1; 153 return 1;
153} 154}
154 155
@@ -1010,42 +1011,6 @@ mlp_solve_lp_problem (struct GAS_MLP_Handle *mlp)
1010 1011
1011 1012
1012/** 1013/**
1013 * Solves the MLP problem
1014 *
1015 * @param mlp the MLP Handle
1016 * @return GNUNET_OK if could be solved, GNUNET_SYSERR on failure
1017 */
1018int
1019mlp_solve_mlp_problem (struct GAS_MLP_Handle *mlp)
1020{
1021 int res = 0;
1022 int res_status = 0;
1023 res = glp_intopt(mlp->p.prob, &mlp->control_param_mlp);
1024 if (0 == res)
1025 LOG(GNUNET_ERROR_TYPE_DEBUG, "Solving MLP problem: 0x%02X %s\n", res,
1026 mlp_solve_to_string (res));
1027 else
1028 LOG(GNUNET_ERROR_TYPE_DEBUG, "Solving MLP problem failed: 0x%02X %s\n", res,
1029 mlp_solve_to_string (res));
1030 /* Analyze problem status */
1031 res_status = glp_mip_status(mlp->p.prob);
1032 switch (res_status) {
1033 case GLP_OPT: /* solution is optimal */
1034 LOG (GNUNET_ERROR_TYPE_INFO,
1035 "Solving MLP problem: 0x%02X %s, 0x%02X %s\n",
1036 res, mlp_solve_to_string(res),
1037 res_status, mlp_status_to_string(res_status));
1038 return GNUNET_OK;
1039 default:
1040 LOG (GNUNET_ERROR_TYPE_WARNING,
1041 "Solving MLP problem failed: 0x%02X %s 0x%02X %s\n",
1042 res, mlp_solve_to_string(res),
1043 res_status, mlp_status_to_string(res_status));
1044 return GNUNET_SYSERR;
1045 }
1046}
1047
1048/**
1049 * Propagates the results when MLP problem was solved 1014 * Propagates the results when MLP problem was solved
1050 * 1015 *
1051 * @param cls the MLP handle 1016 * @param cls the MLP handle
@@ -1176,6 +1141,45 @@ static void notify (struct GAS_MLP_Handle *mlp,
1176 if (NULL != mlp->env->info_cb) 1141 if (NULL != mlp->env->info_cb)
1177 mlp->env->info_cb (mlp->env->info_cb_cls, op, stat, add); 1142 mlp->env->info_cb (mlp->env->info_cb_cls, op, stat, add);
1178} 1143}
1144
1145static void mlp_branch_and_cut_cb (glp_tree *tree, void *info)
1146{
1147 struct GAS_MLP_Handle *mlp = info;
1148
1149 switch (glp_ios_reason (tree))
1150 {
1151 case GLP_ISELECT:
1152 /* Do nothing here */
1153 break;
1154 case GLP_IPREPRO:
1155 /* Do nothing here */
1156 break;
1157 case GLP_IROWGEN:
1158 /* Do nothing here */
1159 break;
1160 case GLP_IHEUR:
1161 /* Do nothing here */
1162 break;
1163 case GLP_ICUTGEN:
1164 /* Do nothing here */
1165 break;
1166 case GLP_IBRANCH:
1167 /* Do nothing here */
1168 break;
1169 case GLP_IBINGO:
1170 /* A better solution was found */
1171 mlp->ps.mlp_gap = glp_ios_mip_gap (tree);
1172 LOG (GNUNET_ERROR_TYPE_ERROR,
1173 "Found better integer solution, current MIP GAP: %f\n", mlp->ps.mlp_gap);
1174
1175 break;
1176 default:
1177 break;
1178 }
1179 //GNUNET_break (0);
1180}
1181
1182
1179/** 1183/**
1180 * Solves the MLP problem 1184 * Solves the MLP problem
1181 * 1185 *
@@ -1188,7 +1192,8 @@ GAS_mlp_solve_problem (void *solver)
1188 struct GAS_MLP_Handle *mlp = solver; 1192 struct GAS_MLP_Handle *mlp = solver;
1189 char *filename; 1193 char *filename;
1190 int res_lp = 0; 1194 int res_lp = 0;
1191 int res_mip = 0; 1195 int mip_res = 0;
1196 int mip_status = 0;
1192 1197
1193 struct GNUNET_TIME_Absolute start_total; 1198 struct GNUNET_TIME_Absolute start_total;
1194 struct GNUNET_TIME_Absolute start_cur_op; 1199 struct GNUNET_TIME_Absolute start_cur_op;
@@ -1254,6 +1259,12 @@ GAS_mlp_solve_problem (void *solver)
1254 LOG(GNUNET_ERROR_TYPE_DEBUG, "Problem was updated, resolving\n"); 1259 LOG(GNUNET_ERROR_TYPE_DEBUG, "Problem was updated, resolving\n");
1255 } 1260 }
1256 1261
1262 /* Reset solution info */
1263 mlp->ps.lp_objective_value = 0.0;
1264 mlp->ps.mlp_gap = 1.0;
1265 mlp->ps.mlp_objective_value = 0.0;
1266
1267
1257 dur_setup = GNUNET_TIME_absolute_get_duration (start_total); 1268 dur_setup = GNUNET_TIME_absolute_get_duration (start_total);
1258 1269
1259 /* Run LP solver */ 1270 /* Run LP solver */
@@ -1289,16 +1300,76 @@ GAS_mlp_solve_problem (void *solver)
1289 start_cur_op = GNUNET_TIME_absolute_get(); 1300 start_cur_op = GNUNET_TIME_absolute_get();
1290 1301
1291 /* Solve MIP */ 1302 /* Solve MIP */
1303
1292 /* Only for debugging, always use MLP presolver */ 1304 /* Only for debugging, always use MLP presolver */
1293 if (GNUNET_YES == mlp->opt_dbg_intopt_presolver) 1305 if (GNUNET_YES == mlp->opt_dbg_intopt_presolver)
1294 mlp->control_param_mlp.presolve = GNUNET_YES; 1306 mlp->control_param_mlp.presolve = GNUNET_YES;
1295 res_mip = mlp_solve_mlp_problem(mlp); 1307
1308
1309 mip_res = glp_intopt (mlp->p.prob, &mlp->control_param_mlp);
1310 switch (mip_res)
1311 {
1312 case 0:
1313 /* Successful */
1314 LOG (GNUNET_ERROR_TYPE_WARNING,
1315 "Solving MLP problem: 0x%02X %s\n",
1316 mip_res, mlp_solve_to_string (mip_res));
1317 break;
1318 case GLP_ETMLIM: /* Time limit reached */
1319 case GLP_EMIPGAP: /* MIP gap tolerance limit reached */
1320 case GLP_ESTOP: /* Solver was instructed to stop*/
1321 /* Semi-successful */
1322 LOG (GNUNET_ERROR_TYPE_WARNING,
1323 "Solving MLP problem solution was interupted: 0x%02X %s\n",
1324 mip_res, mlp_solve_to_string (mip_res));
1325 break;
1326 case GLP_EBOUND:
1327 case GLP_EROOT:
1328 case GLP_ENOPFS:
1329 case GLP_ENODFS:
1330 case GLP_EFAIL:
1331 default:
1332 /* Fail */
1333 LOG (GNUNET_ERROR_TYPE_ERROR,
1334 "Solving MLP problem failed: 0x%02X %s\n",
1335 mip_res, mlp_solve_to_string (mip_res));
1336 break;
1337 }
1338
1339 /* Analyze problem status */
1340 mip_status = glp_mip_status(mlp->p.prob);
1341 switch (mip_status)
1342 {
1343 case GLP_OPT: /* solution is optimal */
1344 LOG (GNUNET_ERROR_TYPE_WARNING,
1345 "Solution of MLP problem is optimal: 0x%02X %s, 0x%02X %s\n",
1346 mip_res, mlp_solve_to_string (mip_res),
1347 mip_status, mlp_status_to_string (mip_status));
1348 mip_res = GNUNET_OK;
1349 break;
1350 case GLP_FEAS: /* solution is feasible but not proven optimal */
1351 LOG (GNUNET_ERROR_TYPE_WARNING,
1352 "Solution of MLP problem is feasible: 0x%02X %s, 0x%02X %s\n",
1353 mip_res, mlp_solve_to_string (mip_res),
1354 mip_status, mlp_status_to_string (mip_status));
1355 mip_res = GNUNET_OK;
1356 break;
1357 case GLP_UNDEF: /* Solution undefined */
1358 case GLP_NOFEAS: /* No feasible solution */
1359 default:
1360 LOG (GNUNET_ERROR_TYPE_ERROR,
1361 "Solving MLP problem failed: 0x%02X %s 0x%02X %s\n",
1362 mip_res, mlp_solve_to_string (mip_res),
1363 mip_status, mlp_status_to_string (mip_status));
1364 mip_res = GNUNET_SYSERR;
1365 break;
1366 }
1296 1367
1297 dur_mlp = GNUNET_TIME_absolute_get_duration (start_cur_op); 1368 dur_mlp = GNUNET_TIME_absolute_get_duration (start_cur_op);
1298 dur_total = GNUNET_TIME_absolute_get_duration (start_total); 1369 dur_total = GNUNET_TIME_absolute_get_duration (start_total);
1299 1370
1300 notify(mlp, GAS_OP_SOLVE_MLP_MLP_STOP, 1371 notify(mlp, GAS_OP_SOLVE_MLP_MLP_STOP,
1301 (GNUNET_OK == res_mip) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL, 1372 (GNUNET_OK == mip_res) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL,
1302 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED); 1373 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED);
1303 } 1374 }
1304 else 1375 else
@@ -1309,12 +1380,12 @@ GAS_mlp_solve_problem (void *solver)
1309 1380
1310 notify(mlp, GAS_OP_SOLVE_MLP_MLP_STOP, GAS_STAT_FAIL, 1381 notify(mlp, GAS_OP_SOLVE_MLP_MLP_STOP, GAS_STAT_FAIL,
1311 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED); 1382 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED);
1312 res_mip = GNUNET_SYSERR; 1383 mip_res = GNUNET_SYSERR;
1313 } 1384 }
1314 1385
1315 /* Notify about end */ 1386 /* Notify about end */
1316 notify(mlp, GAS_OP_SOLVE_STOP, 1387 notify(mlp, GAS_OP_SOLVE_STOP,
1317 ((GNUNET_OK == res_mip) && (GNUNET_OK == res_mip)) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL, 1388 ((GNUNET_OK == mip_res) && (GNUNET_OK == mip_res)) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL,
1318 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED); 1389 (GNUNET_YES == mlp->stat_mlp_prob_changed) ? GAS_INFO_FULL : GAS_INFO_UPDATED);
1319 1390
1320 LOG (GNUNET_ERROR_TYPE_DEBUG, 1391 LOG (GNUNET_ERROR_TYPE_DEBUG,
@@ -1327,7 +1398,7 @@ GAS_mlp_solve_problem (void *solver)
1327 1398
1328 /* Save stats */ 1399 /* Save stats */
1329 mlp->ps.lp_res = res_lp; 1400 mlp->ps.lp_res = res_lp;
1330 mlp->ps.mip_res = res_mip; 1401 mlp->ps.mip_res = mip_res;
1331 mlp->ps.lp_presolv = mlp->control_param_lp.presolve; 1402 mlp->ps.lp_presolv = mlp->control_param_lp.presolve;
1332 mlp->ps.mip_presolv = mlp->control_param_mlp.presolve; 1403 mlp->ps.mip_presolv = mlp->control_param_mlp.presolve;
1333 mlp->ps.p_cols = glp_get_num_cols(mlp->p.prob); 1404 mlp->ps.p_cols = glp_get_num_cols(mlp->p.prob);
@@ -1336,20 +1407,20 @@ GAS_mlp_solve_problem (void *solver)
1336 1407
1337 /* Propagate result*/ 1408 /* Propagate result*/
1338 notify (mlp, GAS_OP_SOLVE_UPDATE_NOTIFICATION_START, 1409 notify (mlp, GAS_OP_SOLVE_UPDATE_NOTIFICATION_START,
1339 (GNUNET_OK == res_lp) && (GNUNET_OK == res_mip) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL, 1410 (GNUNET_OK == res_lp) && (GNUNET_OK == mip_res) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL,
1340 GAS_INFO_NONE); 1411 GAS_INFO_NONE);
1341 if ((GNUNET_OK == res_lp) && (GNUNET_OK == res_mip)) 1412 if ((GNUNET_OK == res_lp) && (GNUNET_OK == mip_res))
1342 { 1413 {
1343 GNUNET_CONTAINER_multipeermap_iterate(mlp->addresses, 1414 GNUNET_CONTAINER_multipeermap_iterate(mlp->addresses,
1344 &mlp_propagate_results, mlp); 1415 &mlp_propagate_results, mlp);
1345 } 1416 }
1346 notify (mlp, GAS_OP_SOLVE_UPDATE_NOTIFICATION_STOP, 1417 notify (mlp, GAS_OP_SOLVE_UPDATE_NOTIFICATION_STOP,
1347 (GNUNET_OK == res_lp) && (GNUNET_OK == res_mip) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL, 1418 (GNUNET_OK == res_lp) && (GNUNET_OK == mip_res) ? GAS_STAT_SUCCESS : GAS_STAT_FAIL,
1348 GAS_INFO_NONE); 1419 GAS_INFO_NONE);
1349 1420
1350 struct GNUNET_TIME_Absolute time = GNUNET_TIME_absolute_get(); 1421 struct GNUNET_TIME_Absolute time = GNUNET_TIME_absolute_get();
1351 if ( (GNUNET_YES == mlp->opt_dump_problem_all) || 1422 if ( (GNUNET_YES == mlp->opt_dump_problem_all) ||
1352 (mlp->opt_dump_problem_on_fail && ((GNUNET_OK != res_lp) || (GNUNET_OK != res_mip))) ) 1423 (mlp->opt_dump_problem_on_fail && ((GNUNET_OK != res_lp) || (GNUNET_OK != mip_res))) )
1353 { 1424 {
1354 /* Write problem to disk */ 1425 /* Write problem to disk */
1355 switch (mlp->opt_log_format) { 1426 switch (mlp->opt_log_format) {
@@ -1375,7 +1446,7 @@ GAS_mlp_solve_problem (void *solver)
1375 GNUNET_free(filename); 1446 GNUNET_free(filename);
1376 } 1447 }
1377 if ( (mlp->opt_dump_solution_all) || 1448 if ( (mlp->opt_dump_solution_all) ||
1378 (mlp->opt_dump_solution_on_fail && ((GNUNET_OK != res_lp) || (GNUNET_OK != res_mip))) ) 1449 (mlp->opt_dump_solution_on_fail && ((GNUNET_OK != res_lp) || (GNUNET_OK != mip_res))) )
1379 { 1450 {
1380 /* Write solution to disk */ 1451 /* Write solution to disk */
1381 GNUNET_asprintf(&filename, "problem_p_%u_a%u_%llu.sol", mlp->p.num_peers, 1452 GNUNET_asprintf(&filename, "problem_p_%u_a%u_%llu.sol", mlp->p.num_peers,
@@ -1390,7 +1461,7 @@ GAS_mlp_solve_problem (void *solver)
1390 mlp->stat_mlp_prob_updated = GNUNET_NO; 1461 mlp->stat_mlp_prob_updated = GNUNET_NO;
1391 mlp->stat_mlp_prob_changed = GNUNET_NO; 1462 mlp->stat_mlp_prob_changed = GNUNET_NO;
1392 1463
1393 if ((GNUNET_OK == res_lp) && (GNUNET_OK == res_mip)) 1464 if ((GNUNET_OK == res_lp) && (GNUNET_OK == mip_res))
1394 return GNUNET_OK; 1465 return GNUNET_OK;
1395 else 1466 else
1396 return GNUNET_SYSERR; 1467 return GNUNET_SYSERR;
@@ -2059,6 +2130,7 @@ libgnunet_plugin_ats_mlp_init (void *cls)
2059 int c; 2130 int c;
2060 int c2; 2131 int c2;
2061 int found; 2132 int found;
2133 char *tmp_str;
2062 char *outputformat; 2134 char *outputformat;
2063 2135
2064 struct GNUNET_TIME_Relative max_duration; 2136 struct GNUNET_TIME_Relative max_duration;
@@ -2218,6 +2290,22 @@ libgnunet_plugin_ats_mlp_init (void *cls)
2218 } 2290 }
2219 2291
2220 mlp->pv.BIG_M = (double) BIG_M_VALUE; 2292 mlp->pv.BIG_M = (double) BIG_M_VALUE;
2293 mlp->pv.mip_gap = (double) 0.0;
2294
2295 if (GNUNET_SYSERR != GNUNET_CONFIGURATION_get_value_string (env->cfg, "ats",
2296 "MLP_MAX_MIP_GAP", &tmp_str))
2297 {
2298 /* Dangerous due to localized separator , or . */
2299 mlp->pv.mip_gap = strtod (tmp_str, NULL);
2300 if ( (mlp->pv.mip_gap < 0.0) && (mlp->pv.mip_gap > 1.0) )
2301 {
2302 LOG (GNUNET_ERROR_TYPE_INFO, "Invalid MIP gap configuration %u \n",
2303 tmp);
2304 }
2305 else
2306 LOG (GNUNET_ERROR_TYPE_WARNING, "Using MIP gap of %.3f\n",
2307 mlp->pv.mip_gap);
2308 }
2221 2309
2222 /* Get timeout for iterations */ 2310 /* Get timeout for iterations */
2223 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_time(env->cfg, "ats", 2311 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_time(env->cfg, "ats",
@@ -2429,7 +2517,11 @@ libgnunet_plugin_ats_mlp_init (void *cls)
2429 2517
2430 /* Init MLP solving parameters */ 2518 /* Init MLP solving parameters */
2431 glp_init_iocp(&mlp->control_param_mlp); 2519 glp_init_iocp(&mlp->control_param_mlp);
2520 /* Setting callback function */
2521 mlp->control_param_mlp.cb_func = &mlp_branch_and_cut_cb;
2522 mlp->control_param_mlp.cb_info = mlp;
2432 mlp->control_param_mlp.msg_lev = GLP_MSG_OFF; 2523 mlp->control_param_mlp.msg_lev = GLP_MSG_OFF;
2524 mlp->control_param_mlp.mip_gap = mlp->pv.mip_gap;
2433 if (GNUNET_YES == mlp->opt_dbg_glpk_verbose) 2525 if (GNUNET_YES == mlp->opt_dbg_glpk_verbose)
2434 mlp->control_param_mlp.msg_lev = GLP_MSG_ALL; 2526 mlp->control_param_mlp.msg_lev = GLP_MSG_ALL;
2435 mlp->control_param_mlp.tm_lim = max_duration.rel_value_us / 1000LL; 2527 mlp->control_param_mlp.tm_lim = max_duration.rel_value_us / 1000LL;
diff --git a/src/ats/plugin_ats_mlp.h b/src/ats/plugin_ats_mlp.h
index b53c0d674..3b5c8f2a0 100644
--- a/src/ats/plugin_ats_mlp.h
+++ b/src/ats/plugin_ats_mlp.h
@@ -71,6 +71,10 @@ struct MLP_Solution
71 int mip_res; 71 int mip_res;
72 int mip_presolv; 72 int mip_presolv;
73 73
74 double lp_objective_value;
75 double mlp_objective_value;
76 double mlp_gap;
77
74 int p_elements; 78 int p_elements;
75 int p_cols; 79 int p_cols;
76 int p_rows; 80 int p_rows;
@@ -156,6 +160,9 @@ struct MLP_Variables
156 /* Big M value for bandwidth capping */ 160 /* Big M value for bandwidth capping */
157 double BIG_M; 161 double BIG_M;
158 162
163 /* MIP Gap */
164 double mip_gap;
165
159 /* ATS Quality metrics 166 /* ATS Quality metrics
160 * 167 *
161 * Array with GNUNET_ATS_QualityPropertiesCount elements 168 * Array with GNUNET_ATS_QualityPropertiesCount elements