Skip to content

Commit 63d3042

Browse files
Add functionality to write to a temp file through url arguments (#5)
1 parent b2cda1d commit 63d3042

File tree

6 files changed

+66
-23
lines changed

6 files changed

+66
-23
lines changed

README.md

+1
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,7 @@ OPTIONS:
7676
-g, --gid Group id to run with
7777
-s, --signal Signal to send to the command when exit it (default: 1, SIGHUP)
7878
-a, --url-arg Allow client to send command line arguments in URL (eg: http://localhost:7681?arg=foo&arg=bar)
79+
-f, --arg-file File prefix for a unique generated temp file that URL arguments are written to (ex. /tmp/prefix); the generated file's full path is then passed in as a command line argument (ex. /tmp/prefix{unique string})
7980
-R, --readonly Do not allow clients to write to the TTY
8081
-t, --client-option Send option to client (format: key=value), repeat to add more options
8182
-T, --terminal-type Terminal type to report, default: xterm-256color

man/ttyd.1

+3
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,9 @@ Cross platform: macOS, Linux, FreeBSD/OpenBSD, OpenWrt/LEDE, Windows
6363
Allow client to send command line arguments in URL (eg:
6464
\[la]http://localhost:7681?arg=foo&arg=bar\[ra])
6565

66+
.PP
67+
\-f, \-\-arg\-file
68+
File prefix for a unique generated temp file that URL arguments are written to (ex. /tmp/prefix); the generated file's full path is then passed in as a command line argument (ex. /tmp/prefix{unique string})
6669
.PP
6770
\-R, \-\-readonly
6871
Do not allow clients to write to the TTY

man/ttyd.man.md

+3
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,9 @@ ttyd 1 "September 2016" ttyd "User Manual"
4040
-a, --url-arg
4141
Allow client to send command line arguments in URL (eg: http://localhost:7681?arg=foo&arg=bar)
4242

43+
-f, --arg-file
44+
File prefix for a unique generated temp file that URL arguments are written to (ex. /tmp/prefix); the generated file's full path is then passed in as a command line argument (ex. /tmp/prefix{unique string})
45+
4346
-R, --readonly
4447
Do not allow clients to write to the TTY
4548

src/protocol.c

+29-3
Original file line numberDiff line numberDiff line change
@@ -100,9 +100,35 @@ static bool spawn_process(struct pss_tty *pss, uint16_t columns, uint16_t rows)
100100
for (i = 0; i < server->argc; i++) {
101101
argv[n++] = server->argv[i];
102102
}
103-
for (i = 0; i < pss->argc; i++) {
104-
argv[n++] = pss->args[i];
103+
if (server->url_arg) {
104+
for (i = 0; i < pss->argc; i++) {
105+
argv[n++] = pss->args[i];
106+
}
107+
} else if (server->arg_file != NULL) {
108+
int fd = -1;
109+
int file_path_len = strlen(server->arg_file) + 6 /*XXXXXX*/ + 1 /*null character*/;
110+
char *filePath = xmalloc(file_path_len);
111+
snprintf(filePath, file_path_len, "%sXXXXXX", server->arg_file);
112+
113+
if ((fd = mkstemp(filePath)) != -1) {
114+
lwsl_err("Creation of temp file failed with error: %d (%s)\n", errno, strerror(errno));
115+
return false;
116+
}
117+
118+
for (i = 0; i < pss->argc; i++) {
119+
if (dprintf(fd, "%s\n", pss->args[i]) < 0) {
120+
lwsl_err("Write to temp file failed with error: %d (%s)\n", errno, strerror(errno));
121+
return false;
122+
}
123+
}
124+
125+
if (close(fd) != 0) {
126+
lwsl_err("Close temp file failed with error: %d (%s)\n", errno, strerror(errno));
127+
return false
128+
}
129+
argv[n++] = filePath;
105130
}
131+
106132
argv[n] = NULL;
107133

108134
pty_process *process = process_init((void *)pss, server->loop, argv);
@@ -181,7 +207,7 @@ int callback_tty(struct lws *wsi, enum lws_callback_reasons reason, void *user,
181207
pss->wsi = wsi;
182208
pss->lws_close_status = LWS_CLOSE_STATUS_NOSTATUS;
183209

184-
if (server->url_arg) {
210+
if (server->url_arg || server->arg_file != NULL) {
185211
while (lws_hdr_copy_fragment(wsi, buf, sizeof(buf), WSI_TOKEN_HTTP_URI_ARGS, n++) > 0) {
186212
if (strncmp(buf, "arg=", 4) == 0) {
187213
pss->args = xrealloc(pss->args, (pss->argc + 1) * sizeof(char *));

src/server.c

+29-20
Original file line numberDiff line numberDiff line change
@@ -62,29 +62,30 @@ static const struct option options[] = {{"port", required_argument, NULL, 'p'},
6262
#if LWS_LIBRARY_VERSION_NUMBER >= 4000000
6363
{"ping-interval", required_argument, NULL, 'P'},
6464
#endif
65-
{"ipv6", no_argument, NULL, '6'},
66-
{"ssl", no_argument, NULL, 'S'},
67-
{"ssl-cert", required_argument, NULL, 'C'},
68-
{"ssl-key", required_argument, NULL, 'K'},
69-
{"ssl-ca", required_argument, NULL, 'A'},
70-
{"url-arg", no_argument, NULL, 'a'},
71-
{"readonly", no_argument, NULL, 'R'},
72-
{"terminal-type", required_argument, NULL, 'T'},
73-
{"client-option", required_argument, NULL, 't'},
74-
{"check-origin", no_argument, NULL, 'O'},
75-
{"max-clients", required_argument, NULL, 'm'},
76-
{"once", no_argument, NULL, 'o'},
77-
{"browser", no_argument, NULL, 'B'},
78-
{"debug", required_argument, NULL, 'd'},
79-
{"version", no_argument, NULL, 'v'},
80-
{"help", no_argument, NULL, 'h'},
81-
{NULL, 0, 0, 0}};
65+
{"ipv6", no_argument, NULL, '6'},
66+
{"ssl", no_argument, NULL, 'S'},
67+
{"ssl-cert", required_argument, NULL, 'C'},
68+
{"ssl-key", required_argument, NULL, 'K'},
69+
{"ssl-ca", required_argument, NULL, 'A'},
70+
{"url-arg", no_argument, NULL, 'a'},
71+
{"arg-file", required_argument, NULL, 'f'},
72+
{"readonly", no_argument, NULL, 'R'},
73+
{"terminal-type", required_argument, NULL, 'T'},
74+
{"client-option", required_argument, NULL, 't'},
75+
{"check-origin", no_argument, NULL, 'O'},
76+
{"max-clients", required_argument, NULL, 'm'},
77+
{"once", no_argument, NULL, 'o'},
78+
{"browser", no_argument, NULL, 'B'},
79+
{"debug", required_argument, NULL, 'd'},
80+
{"version", no_argument, NULL, 'v'},
81+
{"help", no_argument, NULL, 'h'},
82+
{NULL, 0, 0, 0}};
8283

8384
#if LWS_LIBRARY_VERSION_NUMBER < 4000000
84-
static const char *opt_string = "p:i:c:u:g:s:I:b:6aSC:K:A:Rt:T:Om:oBd:vh";
85+
static const char *opt_string = "p:i:c:u:g:s:I:b:6af:SC:K:A:Rt:T:Om:oBd:vh";
8586
#endif
8687
#if LWS_LIBRARY_VERSION_NUMBER >= 4000000
87-
static const char *opt_string = "p:i:c:u:g:s:I:b:P:6aSC:K:A:Rt:T:Om:oBd:vh";
88+
static const char *opt_string = "p:i:c:u:g:s:I:b:P:6af:SC:K:A:Rt:T:Om:oBd:vh";
8889
#endif
8990

9091
static void print_help() {
@@ -102,6 +103,7 @@ static void print_help() {
102103
" -g, --gid Group id to run with\n"
103104
" -s, --signal Signal to send to the command when exit it (default: 1, SIGHUP)\n"
104105
" -a, --url-arg Allow client to send command line arguments in URL (eg: http://localhost:7681?arg=foo&arg=bar)\n"
106+
" -f, --arg-file File prefix for a unique generated temp file that URL arguments are written to (ex. /tmp/prefix); the generated file's full path is then passed in as a command line argument (ex. /tmp/prefix{unique string})\n"
105107
" -R, --readonly Do not allow clients to write to the TTY\n"
106108
" -t, --client-option Send option to client (format: key=value), repeat to add more options\n"
107109
" -T, --terminal-type Terminal type to report, default: xterm-256color\n"
@@ -177,6 +179,7 @@ static struct server *server_new(int argc, char **argv, int start) {
177179

178180
static void server_free(struct server *ts) {
179181
if (ts == NULL) return;
182+
if (ts->arg_file != NULL) free(ts->arg_file);
180183
if (ts->credential != NULL) free(ts->credential);
181184
if (ts->index != NULL) free(ts->index);
182185
free(ts->command);
@@ -326,6 +329,11 @@ int main(int argc, char **argv) {
326329
break;
327330
case 'a':
328331
server->url_arg = true;
332+
server->arg_file = NULL;
333+
break;
334+
case 'f':
335+
server->arg_file = strdup(optarg);
336+
server->url_arg = false;
329337
break;
330338
case 'R':
331339
server->readonly = true;
@@ -527,7 +535,8 @@ int main(int argc, char **argv) {
527535
lwsl_notice(" websocket: %s\n", endpoints.ws);
528536
}
529537
if (server->check_origin) lwsl_notice(" check origin: true\n");
530-
if (server->url_arg) lwsl_notice(" allow url arg: true\n");
538+
if (server->url_arg) lwsl_notice(" allow url arg to cli arg: true\n");
539+
if (server->arg_file != NULL) lwsl_notice(" temp file name prefix: %s\n", server->arg_file);
531540
if (server->readonly) lwsl_notice(" readonly: true\n");
532541
if (server->max_clients > 0) lwsl_notice(" max clients: %d\n", server->max_clients);
533542
if (server->once) lwsl_notice(" once: true\n");

src/server.h

+1
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,7 @@ struct server {
6565
int sig_code; // close signal
6666
char sig_name[20]; // human readable signal string
6767
bool url_arg; // allow client to send cli arguments in URL
68+
char *arg_file; // file prefix for a generated temp file that URL arguments are written to
6869
bool readonly; // whether not allow clients to write to the TTY
6970
bool check_origin; // whether allow websocket connection from different origin
7071
int max_clients; // maximum clients to support

0 commit comments

Comments
 (0)