2019-01-11 15:44:38 +00:00
|
|
|
/**
|
|
|
|
* @file generator.c
|
|
|
|
* @author Ivaylo Ivanov 11777707
|
|
|
|
* @date 11.01.2018
|
|
|
|
*
|
|
|
|
* @brief Generator program module.
|
|
|
|
*
|
|
|
|
* The generator program takes a graph as input. The program repeatedly generates a random solution
|
|
|
|
* to the problem as described on the first page and writes its result to the circular buffer. It repeats this
|
|
|
|
* procedure until it is notified by the supervisor to terminate.
|
|
|
|
* The generator program takes as arguments the set of edges of the graph.
|
|
|
|
* Each positional argument is one edge; at least one edge must be given. An edge is specified by a string,
|
|
|
|
* with the indices of the two nodes it connects separated by a -. Since the graph is directed, the edge starts
|
|
|
|
* at the first node and leads to the second node. Note that the number of nodes of the graph is implicitly
|
|
|
|
* provided through the indices in the edges. In the example above the generator program is called with
|
|
|
|
* the graph shown on the first page.
|
|
|
|
* The generator uses the algorithm described on the first page to generate random feedback arc sets for the
|
|
|
|
* given graph. It writes these feedback arc sets to the circular buffer, one at a time; therefore a feedback
|
|
|
|
* arc set is a single element of the circular buffer. The generator may produce debug output, describing
|
|
|
|
* the feedback arc sets which it writes to the circular buffer.
|
|
|
|
*
|
|
|
|
* SYNOPSIS
|
|
|
|
* generator EDGE1 EDGE2 ...
|
|
|
|
*
|
|
|
|
* EXAMPLE
|
|
|
|
* generator 0-1 1-2 1-3 1-4 2-4 3-6 4-3 4-5 6-0
|
|
|
|
*
|
|
|
|
**/
|
|
|
|
#include "shared/shm.c"
|
2019-01-12 11:39:01 +00:00
|
|
|
#include "shared/sem.c"
|
|
|
|
#include "shared/structs.c"
|
2019-01-11 16:23:54 +00:00
|
|
|
#include <regex.h>
|
2019-01-11 15:44:38 +00:00
|
|
|
|
|
|
|
int main(int argc, char *argv[]) {
|
2019-01-11 16:23:54 +00:00
|
|
|
if(argc < 2) {
|
|
|
|
fprintf(stderr, "ERROR: Command takes at least one argument.\n");
|
|
|
|
puts("Usage: \ngenerator EDGE1 EDGE2 ...");
|
2019-01-11 15:44:38 +00:00
|
|
|
exit(EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
|
2019-01-12 11:39:01 +00:00
|
|
|
/// Create a regex to check the input against
|
2019-01-11 16:23:54 +00:00
|
|
|
regex_t regex;
|
|
|
|
if(regcomp(®ex, "^[0-9]*-[0-9]*$", REG_EXTENDED|REG_NOSUB)) {
|
|
|
|
fprintf(stderr, "ERROR: Could not compile regex\n");
|
|
|
|
exit(EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
|
2019-01-12 11:39:01 +00:00
|
|
|
edge_t edges[argc - 2]; ///< Array to hold the edges
|
|
|
|
|
|
|
|
char edge[128]; ///< Variable to hold a single edge later on
|
|
|
|
edge[127] = 0;
|
|
|
|
|
|
|
|
for(int i=1; i < argc; i++) {
|
|
|
|
/// Check the input and terminate if incorrect
|
2019-01-11 16:23:54 +00:00
|
|
|
if(regexec(®ex, argv[i], 0, NULL, 0) == REG_NOMATCH) {
|
|
|
|
fprintf(stderr, "ERROR: Incorrect input found\n");
|
|
|
|
puts("Usage: \ngenerator EDGE1 EDGE2 ...");
|
|
|
|
exit(EXIT_FAILURE);
|
2019-01-12 11:39:01 +00:00
|
|
|
} else {
|
|
|
|
/// If input is correct, split and add to the edges array
|
|
|
|
strcpy(edge, argv[i]);
|
|
|
|
char *u = strtok(edge, "-");
|
|
|
|
char *v = strtok(NULL, "");
|
|
|
|
edges[i-1].u = strtol(u, NULL, 10);
|
|
|
|
edges[i-1].v = strtol(v, NULL, 10);
|
2019-01-11 16:23:54 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-01-12 11:39:01 +00:00
|
|
|
exit(EXIT_SUCCESS);
|
2019-01-11 15:44:38 +00:00
|
|
|
}
|