Skip to content
Open
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 36 additions & 4 deletions batch_job/src/vine_factory.c
Original file line number Diff line number Diff line change
Expand Up @@ -219,6 +219,34 @@ int manager_workers_capacity(struct jx *j) {
return capacity;
}

char *shell_escape(const char *input) {
size_t len = strlen(input);

// Worst case: every char becomes 2 chars + quotes
char *output = malloc(len * 2 + 3);
Comment on lines +225 to +226
Copy link

Copilot AI Sep 22, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The memory allocation calculation len * 2 + 3 may be insufficient for strings containing many special characters. Consider using a more conservative calculation or dynamic reallocation to prevent buffer overflows.

Suggested change
// Worst case: every char becomes 2 chars + quotes
char *output = malloc(len * 2 + 3);
// First pass: calculate required output size
size_t out_len = 2; // for opening and closing quotes
for (const char *src = input; *src; src++) {
switch (*src) {
case '"':
case '\\':
case '$':
case '`':
case '!':
case '\'':
out_len += 2; // escaped char: backslash + char
break;
default:
out_len += 1;
break;
}
}
out_len += 1; // for null terminator
char *output = malloc(out_len);

Copilot uses AI. Check for mistakes.
if (!output) return NULL;

char *dst = output;
*dst++ = '"'; // open double quote

for (const char *src = input; *src; src++) {
switch (*src) {
case '"': *dst++ = '\\'; *dst++ = '"'; break;
case '\\': *dst++ = '\\'; *dst++ = '\\'; break;
case '$': *dst++ = '\\'; *dst++ = '$'; break;
case '`': *dst++ = '\\'; *dst++ = '`'; break;
case '!': *dst++ = '\\'; *dst++ = '!'; break;
case '\'': *dst++ = '\\'; *dst++ = '\''; break; // escape single quote
default: *dst++ = *src; break;
}
}

*dst++ = '"'; // close double quote
*dst = '\0';

return output;
}

int manager_workers_needed_by_resource(struct jx *j) {
int tasks_total_cores = jx_lookup_integer(j, "tasks_total_cores");
int tasks_total_memory = jx_lookup_integer(j, "tasks_total_memory");
Expand Down Expand Up @@ -468,7 +496,7 @@ static int submit_worker( struct batch_queue *queue )
cmd = string_format(
"./%s --parent-death -M %s -t %d -C '%s' %s %s %s %s %s %s %s %s",
worker_command,
submission_regex,
shell_escape(submission_regex),
worker_timeout,
catalog_host,
debug_workers ? debug_worker_options : "",
Expand All @@ -484,7 +512,7 @@ static int submit_worker( struct batch_queue *queue )
cmd = string_format(
"./%s --parent-death %s %d -t %d -C '%s' %s %s %s %s %s %s %s",
worker_command,
manager_host,
shell_escape(manager_host),
manager_port,
worker_timeout,
catalog_host,
Expand Down Expand Up @@ -1686,7 +1714,9 @@ int main(int argc, char *argv[])

char* cmd;
if(worker_command != NULL){
cmd = string_format("cp '%s' '%s'",worker_command,scratch_dir);
cmd = string_format("cp %s %s",
shell_escape(worker_command),
shell_escape(scratch_dir));
if(system(cmd)){
fprintf(stderr,"vine_factory: Could not Access specified worker binary.\n");
exit(EXIT_FAILURE);
Expand All @@ -1703,7 +1733,9 @@ int main(int argc, char *argv[])
exit(EXIT_FAILURE);
}

cmd = string_format("cp '%s' '%s'",tmp,scratch_dir);
cmd = string_format("cp %s %s",
shell_escape(tmp),
shell_escape(scratch_dir));
if (system(cmd)) {
fprintf(stderr, "vine_factory: could not copy vine_worker to scratch directory.\n");
exit(EXIT_FAILURE);
Expand Down