Pulled some duplicated code out of control.c into
read_lines_until_blankline.
This commit is contained in:
117
control.c
117
control.c
@@ -49,8 +49,9 @@ void* mirror_runner(void* serve_params_uncast)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define write_socket(msg) write(client->socket, (msg "\n"), strlen((msg))+1)
|
||||||
|
|
||||||
void control_mirror(struct control_params* client)
|
int control_mirror(struct control_params* client, int linesc, char** lines)
|
||||||
{
|
{
|
||||||
off64_t size, remote_size;
|
off64_t size, remote_size;
|
||||||
int fd, map_fd;
|
int fd, map_fd;
|
||||||
@@ -58,25 +59,24 @@ void control_mirror(struct control_params* client)
|
|||||||
union mysockaddr connect_to;
|
union mysockaddr connect_to;
|
||||||
char s_ip_address[64], s_port[8];
|
char s_ip_address[64], s_port[8];
|
||||||
|
|
||||||
CLIENT_ERROR_ON_FAILURE(
|
if (linesc != 2) {
|
||||||
read_until_newline(client->socket, s_ip_address, 64),
|
write_socket("1: mirror only takes two parameters");
|
||||||
"Failed to read destination IP"
|
return -1;
|
||||||
);
|
}
|
||||||
CLIENT_ERROR_ON_FAILURE(
|
|
||||||
read_until_newline(client->socket, s_port, 8),
|
if (parse_ip_to_sockaddr(&connect_to.generic, s_ip_address) == 0) {
|
||||||
"Failed to read destination port"
|
write_socket("1: bad IP address");
|
||||||
);
|
return -1;
|
||||||
|
}
|
||||||
if (parse_ip_to_sockaddr(&connect_to.generic, s_ip_address) == 0)
|
|
||||||
CLIENT_ERROR("Couldn't parse connection address '%s'",
|
|
||||||
s_ip_address);
|
|
||||||
|
|
||||||
connect_to.v4.sin_port = atoi(s_port);
|
connect_to.v4.sin_port = atoi(s_port);
|
||||||
if (connect_to.v4.sin_port < 0 || connect_to.v4.sin_port > 65535)
|
if (connect_to.v4.sin_port < 0 || connect_to.v4.sin_port > 65535) {
|
||||||
CLIENT_ERROR("Port number must be >= 0 and <= 65535");
|
write_socket("1: bad IP port number");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
connect_to.v4.sin_port = htobe16(connect_to.v4.sin_port);
|
connect_to.v4.sin_port = htobe16(connect_to.v4.sin_port);
|
||||||
|
|
||||||
fd = socket_connect(&connect_to.generic); /* FIXME uses wrong error handler */
|
fd = socket_connect(&connect_to.generic);
|
||||||
|
|
||||||
remote_size = socket_nbd_read_hello(fd);
|
remote_size = socket_nbd_read_hello(fd);
|
||||||
remote_size = remote_size; // shush compiler
|
remote_size = remote_size; // shush compiler
|
||||||
@@ -110,32 +110,19 @@ void control_mirror(struct control_params* client)
|
|||||||
),
|
),
|
||||||
"Failed to create mirror thread"
|
"Failed to create mirror thread"
|
||||||
);
|
);
|
||||||
|
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void control_acl(struct control_params* client)
|
int control_acl(struct control_params* client, int linesc, char** lines)
|
||||||
{
|
{
|
||||||
int acl_entries = 0, parsed;
|
int acl_entries = 0, parsed;
|
||||||
char** s_acl_entry = NULL;
|
char** s_acl_entry = NULL;
|
||||||
struct ip_and_mask (*acl)[], (*old_acl)[];
|
struct ip_and_mask (*acl)[], (*old_acl)[];
|
||||||
|
|
||||||
while (1) {
|
parsed = parse_acl(&acl, linesc, lines);
|
||||||
char entry[64];
|
if (parsed != linesc) {
|
||||||
int result = read_until_newline(client->socket, entry, 64);
|
write(client->socket, "3: bad spec ", 12);
|
||||||
if (result == -1)
|
|
||||||
goto done;
|
|
||||||
if (result == 1) /* blank line terminates */
|
|
||||||
break;
|
|
||||||
s_acl_entry = xrealloc(
|
|
||||||
s_acl_entry,
|
|
||||||
++acl_entries * sizeof(struct s_acl_entry*)
|
|
||||||
);
|
|
||||||
s_acl_entry[acl_entries-1] = strdup(entry);
|
|
||||||
debug("acl_entry = '%s'", s_acl_entry[acl_entries-1]);
|
|
||||||
}
|
|
||||||
|
|
||||||
parsed = parse_acl(&acl, acl_entries, s_acl_entry);
|
|
||||||
if (parsed != acl_entries) {
|
|
||||||
write(client->socket, "error: ", 7);
|
|
||||||
write(client->socket, s_acl_entry[parsed],
|
write(client->socket, s_acl_entry[parsed],
|
||||||
strlen(s_acl_entry[parsed]));
|
strlen(s_acl_entry[parsed]));
|
||||||
write(client->socket, "\n", 1);
|
write(client->socket, "\n", 1);
|
||||||
@@ -146,43 +133,53 @@ void control_acl(struct control_params* client)
|
|||||||
client->serve->acl = acl;
|
client->serve->acl = acl;
|
||||||
client->serve->acl_entries = acl_entries;
|
client->serve->acl_entries = acl_entries;
|
||||||
free(old_acl);
|
free(old_acl);
|
||||||
write(client->socket, "ok\n", 3);
|
write_socket("0: updated");
|
||||||
}
|
}
|
||||||
|
|
||||||
done: if (acl_entries > 0) {
|
return 0;
|
||||||
int i;
|
|
||||||
for (i=0; i<acl_entries; i++)
|
|
||||||
free(s_acl_entry[i]);
|
|
||||||
free(s_acl_entry);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void control_status(struct control_params* client)
|
int control_status(struct control_params* client, int linesc, char** lines)
|
||||||
{
|
{
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void* control_serve(void* client_uncast)
|
void* control_serve(void* client_uncast)
|
||||||
{
|
{
|
||||||
const int max = 256;
|
|
||||||
char command[max];
|
|
||||||
struct control_params* client = (struct control_params*) client_uncast;
|
struct control_params* client = (struct control_params*) client_uncast;
|
||||||
|
char **lines = NULL;
|
||||||
|
int finished=0;
|
||||||
|
|
||||||
while (1) {
|
while (!finished) {
|
||||||
CLIENT_ERROR_ON_FAILURE(
|
int i, linesc;
|
||||||
read_until_newline(client->socket, command, max),
|
linesc = read_lines_until_blankline(client->socket, 256, &lines);
|
||||||
"Error reading command"
|
|
||||||
);
|
|
||||||
|
|
||||||
if (strcmp(command, "acl") == 0)
|
if (linesc < 1)
|
||||||
control_acl(client);
|
{
|
||||||
else if (strcmp(command, "mirror") == 0)
|
write(client->socket, "9: missing command\n", 19);
|
||||||
control_mirror(client);
|
finished = 1;
|
||||||
else if (strcmp(command, "status") == 0)
|
/* ignore failure */
|
||||||
control_status(client);
|
|
||||||
else {
|
|
||||||
write(client->socket, "error: unknown command\n", 23);
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
|
else if (strcmp(lines[0], "acl") == 0) {
|
||||||
|
if (control_acl(client, linesc-1, lines+1) < 0)
|
||||||
|
finished = 1;
|
||||||
|
}
|
||||||
|
else if (strcmp(lines[0], "mirror") == 0) {
|
||||||
|
if (control_mirror(client, linesc-1, lines+1) < 0)
|
||||||
|
finished = 1;
|
||||||
|
}
|
||||||
|
else if (strcmp(lines[0], "status") == 0) {
|
||||||
|
if (control_status(client, linesc-1, lines+1) < 0)
|
||||||
|
finished = 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
write(client->socket, "10: unknown command\n", 23);
|
||||||
|
finished = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i=0; i<linesc; i++)
|
||||||
|
free(lines[i]);
|
||||||
|
free(lines);
|
||||||
}
|
}
|
||||||
|
|
||||||
close(client->socket);
|
close(client->socket);
|
||||||
|
18
ioutil.c
18
ioutil.c
@@ -184,3 +184,21 @@ int read_until_newline(int fd, char* buf, int bufsize)
|
|||||||
|
|
||||||
return cur;
|
return cur;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int read_lines_until_blankline(int fd, int max_line_length, char ***lines)
|
||||||
|
{
|
||||||
|
int lines_count = 0;
|
||||||
|
char line[max_line_length+1];
|
||||||
|
*lines = NULL;
|
||||||
|
|
||||||
|
while (1) {
|
||||||
|
if (read_until_newline(fd, line, max_line_length) < 0)
|
||||||
|
return lines_count;
|
||||||
|
*lines = xrealloc(*lines, (lines_count+1) * sizeof(char*));
|
||||||
|
(*lines)[lines_count] = strdup(line);
|
||||||
|
if ((*lines)[lines_count][0] == 0)
|
||||||
|
return lines_count;
|
||||||
|
lines_count++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
1
ioutil.h
1
ioutil.h
@@ -10,6 +10,7 @@ int readloop(int filedes, void *buffer, size_t size);
|
|||||||
int sendfileloop(int out_fd, int in_fd, off64_t *offset, size_t count);
|
int sendfileloop(int out_fd, int in_fd, off64_t *offset, size_t count);
|
||||||
int splice_via_pipe_loop(int fd_in, int fd_out, size_t len);
|
int splice_via_pipe_loop(int fd_in, int fd_out, size_t len);
|
||||||
int read_until_newline(int fd, char* buf, int bufsize);
|
int read_until_newline(int fd, char* buf, int bufsize);
|
||||||
|
int read_lines_until_blankline(int fd, int max_line_length, char ***lines);
|
||||||
int open_and_mmap(char* filename, int* out_fd, off64_t *out_size, void **out_map);
|
int open_and_mmap(char* filename, int* out_fd, off64_t *out_size, void **out_map);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Reference in New Issue
Block a user