1 /* Written by Anthony Liguori <aliguori@us.ibm.com> */
2 
3 #include <stdio.h>
4 #include <stdlib.h>
5 #include <time.h>
6 #include <string.h>
7 #include <unistd.h>
8 #include <termios.h>
9 
10 #define MIN(a, b) (((a) < (b)) ? (a) : (b))
11 
generate_random_buffer(char * buffer,size_t size)12 static void generate_random_buffer(char *buffer, size_t size)
13 {
14 	int i;
15 
16 	for (i = 0; i < size; i++) {
17 		buffer[i] = random() & 0xFF;
18 	}
19 }
20 
canonicalize(char * buffer)21 static void canonicalize(char *buffer)
22 {
23 	char *reader, *writer;
24 
25 	reader = writer = buffer;
26 
27 	while (*reader) {
28 		*writer = *reader;
29 		if (*reader != '\r') writer++;
30 		reader++;
31 	}
32 	*writer = *reader;
33 }
34 
main(int argc,char ** argv)35 int main(int argc, char **argv)
36 {
37 	char buffer[4096];
38 	char *line;
39 	unsigned int seed;
40 	size_t size;
41 	int runs;
42 	unsigned long long total_bytes = 0;
43 	struct termios term;
44 
45 	tcgetattr(STDIN_FILENO, &term);
46 	cfmakeraw(&term);
47 	tcsetattr(STDIN_FILENO, TCSAFLUSH, &term);
48 
49 	tcgetattr(STDOUT_FILENO, &term);
50 	cfmakeraw(&term);
51 	tcsetattr(STDOUT_FILENO, TCSAFLUSH, &term);
52 
53 	while ((line = fgets(buffer, sizeof(buffer), stdin))) {
54 		canonicalize(line);
55 
56 		if (strcmp(line, "!!!XEN Test Begin!!!\n") == 0) {
57 			break;
58 		} else {
59 			fprintf(stderr, "%s", line);
60 		}
61 	}
62 
63 	if (line == NULL) {
64 		fprintf(stderr, "Client never sent start string.\n");
65 		return 1;
66 	}
67 
68 	seed = time(0);
69 
70 	printf("%u\n", seed); fflush(stdout);
71 
72 	fprintf(stderr, "Waiting for seed acknowledgement\n");
73 	line = fgets(buffer, sizeof(buffer), stdin);
74 	if (line == NULL) {
75 		fprintf(stderr, "Client never acknowledge seed.\n");
76 		return 1;
77 	}
78 
79 	canonicalize(line);
80 	if (strcmp(line, "Seed Okay.\n") != 0) {
81 		fprintf(stderr, "Incorrect seed acknowledgement.\n");
82 		fprintf(stderr, "[%s]", line);
83 		return 1;
84 	} else {
85 		fprintf(stderr, "Processed seed.\n");
86 	}
87 
88 	srandom(seed);
89 
90 	for (runs = (random() % 100000) + 4096; runs > 0; runs--) {
91 
92 		size = random() % 4096;
93 
94 		fprintf(stderr, "Writing %d bytes.\n", size);
95 
96 		generate_random_buffer(buffer, size);
97 		fwrite(buffer, size, 1, stdout);
98 		fflush(stdout);
99 
100 		do {
101 			line = fgets(buffer, sizeof(buffer), stdin);
102 			if (line == NULL) {
103 				fprintf(stderr, "Premature EOF from client.\n");
104 				return 1;
105 			}
106 
107 			canonicalize(line);
108 			fprintf(stderr, "%s", line);
109 		} while (strcmp(line, "Okay.\n") != 0);
110 
111 		total_bytes += size;
112 	}
113 
114 	fprintf(stderr, "PASS: processed %llu byte(s).\n", total_bytes);
115 
116 	return 0;
117 }
118