-// unfinished load testing utility for Citadel Server
+// Load testing utility for Citadel Server
//
// Copyright (c) 1987-2023 by the citadel.org team
//
"tempor","tincidunt","phasellus","justo","purus","pharetra","ut","ultricies","nec","consequat","vel",
"nisi","fusce","vitae","velit","at","libero","sollicitudin","sodales","aenean","mi","libero","ultrices",
"id","suscipit","vitae","dapibus","eu","metus","aenean","vestibulum","nibh","ac","massa","vivamus",
- "vestibulum","libero","vitae","purus","in","hac","habitasse","platea","dictumst","curabitur",
+ "vestibulum","libero","vitae","purus","in","hac","maga","habitasse","platea","dictumst","curabitur",
"blandit","nunc","non","arcu","ut","nec","nibh","morbi","quis","leo","vel","magna","commodo","rhoncus",
"donec","congue","leo","eu","lacus","pellentesque","at","erat","id","mi","consequat","congue","praesent",
"a","nisl","ut","diam","interdum","molestie","fusce","suscipit","rhoncus","sem","donec","pretium",
s = socket(AF_UNIX, SOCK_STREAM, 0);
if (s < 0) {
- fprintf(stderr, "loadtest: Can't create socket: %s\n", strerror(errno));
- exit(3);
+ return(-1);
}
if (connect(s, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
- fprintf(stderr, "loadtest: can't connect: %s\n", strerror(errno));
close(s);
- exit(3);
+ return(-1);
}
- return s;
+ return(s);
}
}
-
char *random_rooms[] = {
"Load Testing Test Room One",
"Load Test 2: Electric Boogaloo",
"Five Guys Load Testing and Fries"
};
int nrooms = sizeof(random_rooms) / sizeof(char *);
-
char *test_user = "Load Test User";
+char test_pass[16];
+
+// These are our randomized load test operations: an even mix of changing rooms, posting messages, and deleting messages.
void perform_random_thing(int serv_sock) {
int op = random() % 3;
char buf[SIZ];
}
-void do_stuff(int serv_sock) {
- int i;
+// This is the main loop. We log in as the load test user, and then perform random operations until stopped.
+void *loadtest(void *blah) {
char buf[SIZ];
+ int serv_sock;
+
+ serv_sock = uds_connectsock(file_citadel_socket);
+
+ if (serv_sock < 0) {
+ printf("\033[8;0H\033[31mWarning: some threads failed to connect to Citadel Server.\033[0m");
+ fflush(stdout);
+ pthread_exit(NULL);
+ }
- snprintf(buf, sizeof buf, "CREU %s", test_user);
- serv_puts(serv_sock, buf);
- serv_gets(serv_sock, buf);
- snprintf(buf, sizeof buf, "ASUP %s|640k_enough_ne1|0|||6|", test_user);
- serv_puts(serv_sock, buf);
serv_gets(serv_sock, buf);
snprintf(buf, sizeof buf, "USER %s", test_user);
serv_puts(serv_sock, buf);
serv_gets(serv_sock, buf);
- snprintf(buf, sizeof buf, "PASS 640k_enough_ne1");
+ snprintf(buf, sizeof buf, "PASS %s", test_pass);
serv_puts(serv_sock, buf);
serv_gets(serv_sock, buf);
-
- for (i=0; i<nrooms; ++i) {
- snprintf(buf, sizeof buf, "CRE8 1|%s|", random_rooms[i]);
- serv_puts(serv_sock, buf);
- serv_gets(serv_sock, buf);
- }
-
snprintf(buf, sizeof(buf), "GOTO %s", random_rooms[0]);
serv_puts(serv_sock, buf);
serv_gets(serv_sock, buf);
- printf("\033[%d;0H\033[33m%ld\033[0m", 7+serv_sock, serv_sock-3);
-
+ // Find a nice spot on the screen to show the operation count for this thread.
+ int row = 10 + ((serv_sock-3) % 20);
+ int col = ((serv_sock-3) / 20) * 10;
long ops = 0;
+ printf("\033[%d;%dH\033[33m 0\033[0m", row, col);
+ fflush(stdout);
+
while(1) {
- alarm(30);
perform_random_thing(serv_sock);
- printf("\033[%d;5H\033[33m%8ld\033[0m", 7+serv_sock, ++ops);
+ printf("\033[%d;%dH\033[32m%8ld\033[0m", row, col, ++ops);
fflush(stdout);
}
}
-void *loadtest(void *blah) {
+
+// Create (or replace) the account used for load testing, then create the rooms in which we will load test.
+void setup_accounts(int serv_sock) {
+ int i;
char buf[SIZ];
- int serv_sock;
- serv_sock = uds_connectsock(file_citadel_admin_socket);
+ snprintf(buf, sizeof buf, "CREU %s", test_user);
+ serv_puts(serv_sock, buf);
+ serv_gets(serv_sock, buf);
+ snprintf(buf, sizeof buf, "ASUP %s|%s|0|||6|", test_user, test_pass);
+ serv_puts(serv_sock, buf);
+ serv_gets(serv_sock, buf);
+ snprintf(buf, sizeof buf, "USER %s", test_user);
+ serv_puts(serv_sock, buf);
+ serv_gets(serv_sock, buf);
+ snprintf(buf, sizeof buf, "PASS %s", test_pass);
+ serv_puts(serv_sock, buf);
serv_gets(serv_sock, buf);
- do_stuff(serv_sock);
-
- close(serv_sock);
+ for (i=0; i<nrooms; ++i) {
+ snprintf(buf, sizeof buf, "CRE8 1|%s|", random_rooms[i]);
+ serv_puts(serv_sock, buf);
+ serv_gets(serv_sock, buf);
+ }
}
// Main loop. Do things and have fun.
int main(int argc, char **argv) {
- int a;
+ int i;
int nthreads = 3;
+ int row, col;
fprintf(stderr, "\033[2J\033[H"
- "\033[44m\033[33m\033[1m \033[K\033[0m\n"
- "\033[44m\033[33m\033[1m Load testing utility for Citadel \033[K\033[0m\n"
- "\033[44m\033[33m\033[1m Copyright (c) 2023 by citadel.org et al. \033[K\033[0m\n"
+ "\033[44m\033[33m\033[1m \033[K\033[0m\n"
+ "\033[44m\033[33m\033[1m Load testing utility for Citadel \033[K\033[0m\n"
+ "\033[44m\033[33m\033[1m Copyright (c) 2023 by citadel.org et al. \033[K\033[0m\n"
"\033[44m\033[33m\033[1m This program is open source software. Use, duplication, or disclosure \033[K\033[0m\n"
- "\033[44m\033[33m\033[1m is subject to the terms of the GNU General Public license v3. \033[K\033[0m\n"
- "\033[44m\033[33m\033[1m \033[K\033[0m\n");
+ "\033[44m\033[33m\033[1m is subject to the terms of the GNU General Public license v3. \033[K\033[0m\n"
+ "\033[44m\033[33m\033[1m \033[K\033[0m\n");
// Parse command line
- while ((a = getopt(argc, argv, "h:n:")) != EOF) {
- switch (a) {
+ while ((i = getopt(argc, argv, "h:n:")) != EOF) {
+ switch (i) {
case 'h':
strncpy(ctdldir, optarg, sizeof ctdldir);
break;
exit(errno);
}
- for (a=0; a<(nthreads-1); ++a) {
+ // Generate a random password for load test user. No one needs this password except us.
+ srand(time(NULL)+getpid());
+ for (i=0; i<sizeof(test_pass)-1; ++i) {
+ test_pass[i] = (rand() % 74) + 48;
+ }
+ test_pass[sizeof(test_pass)] = 0;
+
+ // paint the screen
+ for (i=0; i<nthreads; ++i) {
+ row = 10 + (i % 20);
+ col = (i / 20) * 10;
+ printf("\033[%d;%dH\033[31m--------\033[0m", row, col);
+ fflush(stdout);
+ }
+
+ // start connecting
+ int serv_sock = uds_connectsock(file_citadel_admin_socket);
+ if (serv_sock < 0) {
+ fprintf(stderr, "loadtest: cannot connect to Citadel Server\n");
+ exit(1);
+ }
+
+ char buf[SIZ];
+ serv_gets(serv_sock, buf);
+ setup_accounts(serv_sock);
+ close(serv_sock);
+
+ for (i=0; i<(nthreads-1); ++i) {
+
pthread_t thread;
pthread_attr_t attr;
int ret = 0;
}
loadtest(NULL);
-
return(0);
}