2 #include <barvinok/options.h>
3 #include <barvinok/util.h>
7 struct argp_option argp_options
[] = {
19 struct barvinok_options
*barvinok
;
22 static error_t
parse_opt(int key
, char *arg
, struct argp_state
*state
)
24 struct arguments
*options
= (struct arguments
*) state
->input
;
28 state
->child_inputs
[0] = options
->barvinok
;
29 options
->keep_going
= 0;
30 options
->print_max
= 0;
34 options
->keep_going
= 1;
37 options
->print_max
= 1;
43 return ARGP_ERR_UNKNOWN
;
49 #define LS_P 2 /* continue searching P */
50 #define LS_D 4 /* continue searching D */
52 static int check_lexsmaller(Polyhedron
*SP
, Polyhedron
*SD
, Enumeration
*en
,
53 int pos
, int nvar
, Value
*zP
, Value
*zD
, Value
*zE
,
54 Value
*count
, struct arguments
*options
)
58 Value PLB
, PUB
, DLB
, DUB
, LB
, UB
, tmp
, c
;
61 return LS_OK
| LS_P
| LS_D
;
63 value_init(PLB
); value_init(PUB
);
64 value_init(DLB
); value_init(DUB
);
65 value_init(LB
); value_init(UB
);
69 ok
= !(lower_upper_bounds(1+pos
, SP
, zP
, &PLB
, &PUB
));
73 ok
= !(lower_upper_bounds(1+pos
, SD
, zD
, &DLB
, &DUB
));
76 if (!SD
|| (SP
&& value_lt(PLB
, DLB
)))
77 value_assign(LB
, PLB
);
79 value_assign(LB
, DLB
);
80 if (!SD
|| (SP
&& value_gt(PUB
, DUB
)))
81 value_assign(UB
, PUB
);
83 value_assign(UB
, DUB
);
88 ok
= LS_OK
| LS_P
| LS_D
;
90 for(value_assign(tmp
,LB
); value_le(tmp
,UB
); value_increment(tmp
,tmp
)) {
91 int inP
= SP
&& value_ge(tmp
, PLB
) && value_le(tmp
, PUB
);
92 int inD
= SD
&& value_ge(tmp
, DLB
) && value_le(tmp
, DUB
);
97 value_assign(zP
[pos
+1], tmp
);
99 value_assign(zD
[pos
+1], tmp
);
100 if (inD
&& pos
< nvar
)
101 value_assign(zE
[pos
], tmp
);
103 if (inD
&& !SD
->next
) {
106 value_assign(c
,*(ctmp
=compute_poly(en
, zE
)));
110 if (options
->barvinok
->verbose
>= 2) {
112 value_print(stdout
, VALUE_FMT
, zE
[0]);
113 for (i
= 1; i
< nvar
; ++i
) {
115 value_print(stdout
, VALUE_FMT
, zE
[i
]);
118 value_print(stdout
, VALUE_FMT
, c
);
119 printf("; count = ");
120 value_print(stdout
, VALUE_FMT
, *count
);
124 if (value_ne(c
, *count
)) {
127 fprintf(stderr
,"Error !\n");
128 fprintf(stderr
, "EP( ");
129 value_print(stderr
, VALUE_FMT
, zE
[0]);
130 for (i
= 1; i
< nvar
; ++i
) {
131 fprintf(stderr
, ", ");
132 value_print(stderr
, VALUE_FMT
, zE
[i
]);
134 fprintf(stderr
, " ) = ");
135 value_print(stderr
, VALUE_FMT
, c
);
136 fprintf(stderr
, " but count = ");
137 value_print(stderr
, VALUE_FMT
, *count
);
143 value_decrement(*count
, *count
);
149 ok
&= check_lexsmaller(inP
? SP
->next
: NULL
,
150 inD
? SD
->next
: NULL
,
151 en
, pos
+1, nvar
, zP
, zD
, zE
, count
,
154 ok
&= check_lexsmaller(NULL
, inD
? SD
->next
: NULL
,
155 en
, pos
+1, nvar
, zP
, zD
, zE
, count
,
157 & check_lexsmaller(inP
? SP
->next
: NULL
, NULL
,
158 en
, pos
+1, nvar
, zP
, zD
, zE
, count
,
160 if (pos
>= nvar
&& !(ok
& LS_D
))
162 if (pos
>= nvar
&& !(ok
& LS_P
))
166 if (!ok
&& !options
->keep_going
)
169 if (inP
&& !SP
->next
) {
170 value_increment(*count
, *count
);
171 if (value_gt(*count
, options
->max
))
172 value_assign(options
->max
, *count
);
177 value_set_si(zP
[pos
+1], 0);
179 value_set_si(zD
[pos
+1], 0);
185 value_clear(PLB
); value_clear(PUB
);
186 value_clear(DLB
); value_clear(DUB
);
187 value_clear(LB
); value_clear(UB
);
193 int main(int argc
,char *argv
[])
196 Polyhedron
*P
, *D
, *C
;
199 const char **param_name
= NULL
;
202 Vector
*zP
, *zD
, *zE
;
206 struct arguments options
;
207 static struct argp_child argp_children
[] = {
208 { &barvinok_argp
, 0, 0, 0 },
211 static struct argp argp
= { argp_options
, parse_opt
, 0, 0, argp_children
};
212 struct barvinok_options
*bv_options
= barvinok_options_new_with_defaults();
214 options
.barvinok
= bv_options
;
215 set_program_name(argv
[0]);
216 argp_parse(&argp
, argc
, argv
, 0, 0, &options
);
219 P
= Constraints2Polyhedron(M
, bv_options
->MaxRays
);
223 D
= Constraints2Polyhedron(M
, bv_options
->MaxRays
);
227 fgets(s
, 128, stdin
);
228 while ((*s
=='#') || (sscanf(s
, "D %u", &dim
)<1))
229 fgets(s
, 128, stdin
);
232 C
= Constraints2Polyhedron(M
, bv_options
->MaxRays
);
236 nb_parms
= D
->Dimension
;
237 param_name
= Read_ParamNames(stdin
, nb_parms
);
239 EP
= barvinok_lexsmaller_ev(P
, D
, dim
, C
, bv_options
->MaxRays
);
242 evalue
*EC
= barvinok_lexsmaller_ev(D
, D
, dim
, C
, bv_options
->MaxRays
);
243 if (options
.barvinok
->verbose
>= 2) {
245 print_evalue(stdout
, EP
, (const char **)param_name
);
247 print_evalue(stdout
, EC
, (const char **)param_name
);
250 evalue_set_si(&mone
, -1, 1);
253 free_evalue_refs(&mone
);
257 if (bv_options
->verbose
>= 1) {
259 print_evalue(stdout
, EP
, (const char **)param_name
);
261 en
= partition2enumeration(EP
);
263 assert(C
->Dimension
== 0); /* for now */
265 /* S = scanning list of polyhedra */
266 SP
= Polyhedron_Scan(P
, C
, bv_options
->MaxRays
);
267 SD
= Polyhedron_Scan(D
, C
, bv_options
->MaxRays
);
269 zP
= Vector_Alloc(1+P
->Dimension
+1);
270 value_set_si(zP
->p
[1+P
->Dimension
], 1);
271 zD
= Vector_Alloc(1+D
->Dimension
+1);
272 value_set_si(zD
->p
[1+D
->Dimension
], 1);
273 zE
= Vector_Alloc(dim
+C
->Dimension
);
275 if (options
.print_max
)
276 value_init(options
.max
);
278 check_lexsmaller(SP
, SD
, en
, 0, dim
, zP
->p
, zD
->p
, zE
->p
, &count
, &options
);
281 if (options
.print_max
) {
283 value_print(stdout
, VALUE_FMT
, options
.max
);
285 value_clear(options
.max
);
288 Enumeration_Free(en
);
289 Free_ParamNames(param_name
, nb_parms
);
298 barvinok_options_free(bv_options
);