* lisp/autoinsert.el (auto-insert-alist): Fix readability
[bpt/emacs.git] / lib-src / emacsclient.c
CommitLineData
efb859b4 1/* Client process that communicates with GNU Emacs acting as server.
92b47a4a 2 Copyright (C) 1986, 1987, 1994, 1999, 2000, 2001, 2002, 2003, 2004,
114f9c96 3 2005, 2006, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
46cec291
RS
4
5This file is part of GNU Emacs.
6
294981c7 7GNU Emacs is free software: you can redistribute it and/or modify
46cec291 8it under the terms of the GNU General Public License as published by
294981c7
GM
9the Free Software Foundation, either version 3 of the License, or
10(at your option) any later version.
46cec291
RS
11
12GNU Emacs is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
294981c7 18along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
46cec291
RS
19
20
e69233c2 21#ifdef HAVE_CONFIG_H
2f8fe2f4 22#include <config.h>
e69233c2
PJ
23#endif
24
aa0b6932 25#ifdef WINDOWSNT
aa0b6932 26
bc28de71
JB
27/* config.h defines these, which disables sockets altogether! */
28# undef _WINSOCKAPI_
29# undef _WINSOCK_H
30
411b80a5
JB
31# include <malloc.h>
32# include <stdlib.h>
42073bfb 33# include <windows.h>
dbf60b07 34# include <commctrl.h>
411b80a5 35
411b80a5
JB
36# define NO_SOCKETS_IN_FILE_SYSTEM
37
aa0b6932
JB
38# define HSOCKET SOCKET
39# define CLOSE_SOCKET closesocket
aa0b6932 40# define INITIALIZE() (initialize_sockets ())
411b80a5
JB
41
42#else /* !WINDOWSNT */
43
67c1df01 44# include "syswait.h"
ed4a3730 45
1e7823d0
JB
46# ifdef HAVE_INET_SOCKETS
47# include <netinet/in.h>
48# endif
411b80a5 49
18d2ad29 50# include <arpa/inet.h>
448d4085 51
e35fc962 52# define INVALID_SOCKET -1
aa0b6932
JB
53# define HSOCKET int
54# define CLOSE_SOCKET close
aa0b6932 55# define INITIALIZE()
411b80a5 56
5445ab06
DN
57# ifndef WCONTINUED
58# define WCONTINUED 8
59# endif
60
411b80a5 61#endif /* !WINDOWSNT */
aa0b6932 62
4e23f2ba 63#undef signal
46cec291 64
42073bfb 65#include <stdarg.h>
e69233c2 66#include <ctype.h>
8f9aaa0a 67#include <stdio.h>
aa0b6932 68#include "getopt.h"
79f13bba
DL
69#ifdef HAVE_UNISTD_H
70#include <unistd.h>
71#endif
8f9aaa0a 72
aa0b6932
JB
73#ifdef WINDOWSNT
74# include <io.h>
75#else /* not WINDOWSNT */
9f637eea 76# include <pwd.h>
aa0b6932 77#endif /* not WINDOWSNT */
dc4a4a14 78#include <sys/stat.h>
9f637eea 79
9628b887 80#include <signal.h>
4d553a13 81#include <errno.h>
9628b887
KL
82
83\f
8f9aaa0a 84char *getenv (), *getwd ();
5b9562c3 85char *(getcwd) ();
8f9aaa0a 86
7ce8671d
JB
87#ifdef WINDOWSNT
88char *w32_getenv ();
89#define egetenv(VAR) w32_getenv(VAR)
90#else
91#define egetenv(VAR) getenv(VAR)
92#endif
93
8f9aaa0a
RS
94#ifndef VERSION
95#define VERSION "unspecified"
96#endif
97\f
aa0b6932
JB
98
99#ifndef EXIT_SUCCESS
100#define EXIT_SUCCESS 0
101#endif
102
103#ifndef EXIT_FAILURE
104#define EXIT_FAILURE 1
105#endif
106
107#ifndef FALSE
108#define FALSE 0
109#endif
110
111#ifndef TRUE
112#define TRUE 1
113#endif
114
115#ifndef NO_RETURN
116#define NO_RETURN
117#endif
bc558f3e
JB
118
119/* Additional space when allocating buffers for filenames, etc. */
120#define EXTRA_SPACE 100
121
aa0b6932 122\f
8f9aaa0a
RS
123/* Name used to invoke this program. */
124char *progname;
125
0a125897
KL
126/* The second argument to main. */
127char **main_argv;
128
749ae770 129/* Nonzero means don't wait for a response from Emacs. --no-wait. */
8f9aaa0a
RS
130int nowait = 0;
131
30be2360
SM
132/* Nonzero means args are expressions to be evaluated. --eval. */
133int eval = 0;
134
31fa6595
SM
135/* Nonzero means don't open a new frame. Inverse of --create-frame. */
136int current_frame = 1;
92071250 137
30be2360
SM
138/* The display on which Emacs should work. --display. */
139char *display = NULL;
140
0191e222
CY
141/* The parent window ID, if we are opening a frame via XEmbed. */
142char *parent_id = NULL;
143
9628b887 144/* Nonzero means open a new Emacs frame on the current terminal. */
77134727 145int tty = 0;
9628b887 146
30be2360
SM
147/* If non-NULL, the name of an editor to fallback to if the server
148 is not running. --alternate-editor. */
b03d27bd 149const char *alternate_editor = NULL;
30be2360 150
3db926be 151/* If non-NULL, the filename of the UNIX socket. */
254107e4
RS
152char *socket_name = NULL;
153
aa0b6932
JB
154/* If non-NULL, the filename of the authentication file. */
155char *server_file = NULL;
156
c66648e0
JB
157/* PID of the Emacs server process. */
158int emacs_pid = 0;
159
2381d38d 160void print_help_and_exit () NO_RETURN;
7f3bff3e 161
8f9aaa0a
RS
162struct option longopts[] =
163{
749ae770 164 { "no-wait", no_argument, NULL, 'n' },
30be2360 165 { "eval", no_argument, NULL, 'e' },
8f9aaa0a
RS
166 { "help", no_argument, NULL, 'H' },
167 { "version", no_argument, NULL, 'V' },
b28c910d 168 { "tty", no_argument, NULL, 't' },
dc1cd5f7 169 { "nw", no_argument, NULL, 't' },
31fa6595 170 { "create-frame", no_argument, NULL, 'c' },
3cf8c6aa 171 { "alternate-editor", required_argument, NULL, 'a' },
b03d27bd 172#ifndef NO_SOCKETS_IN_FILE_SYSTEM
254107e4 173 { "socket-name", required_argument, NULL, 's' },
b03d27bd 174#endif
aa0b6932 175 { "server-file", required_argument, NULL, 'f' },
0ebec7d3 176#ifndef WINDOWSNT
30be2360 177 { "display", required_argument, NULL, 'd' },
0ebec7d3 178#endif
0191e222 179 { "parent-id", required_argument, NULL, 'p' },
30be2360 180 { 0, 0, 0, 0 }
8f9aaa0a
RS
181};
182
974b73e8
KL
183\f
184/* Like malloc but get fatal error if memory is exhausted. */
185
186long *
187xmalloc (size)
188 unsigned int size;
189{
190 long *result = (long *) malloc (size);
191 if (result == NULL)
192 {
193 perror ("malloc");
194 exit (EXIT_FAILURE);
195 }
196 return result;
197}
198
199/* Like strdup but get a fatal error if memory is exhausted. */
200
201char *
202xstrdup (const char *s)
203{
204 char *result = strdup (s);
205 if (result == NULL)
206 {
207 perror ("strdup");
208 exit (EXIT_FAILURE);
209 }
210 return result;
211}
212
213/* From sysdep.c */
214#if !defined (HAVE_GET_CURRENT_DIR_NAME) || defined (BROKEN_GET_CURRENT_DIR_NAME)
215
cb06b8dc
SM
216/* From lisp.h */
217#ifndef DIRECTORY_SEP
218#define DIRECTORY_SEP '/'
219#endif
220#ifndef IS_DIRECTORY_SEP
221#define IS_DIRECTORY_SEP(_c_) ((_c_) == DIRECTORY_SEP)
222#endif
223#ifndef IS_DEVICE_SEP
224#ifndef DEVICE_SEP
225#define IS_DEVICE_SEP(_c_) 0
226#else
227#define IS_DEVICE_SEP(_c_) ((_c_) == DEVICE_SEP)
228#endif
229#endif
230#ifndef IS_ANY_SEP
231#define IS_ANY_SEP(_c_) (IS_DIRECTORY_SEP (_c_))
232#endif
233
234
974b73e8 235/* Return the current working directory. Returns NULL on errors.
5ab73228 236 Any other returned value must be freed with free. This is used
974b73e8
KL
237 only when get_current_dir_name is not defined on the system. */
238char*
239get_current_dir_name ()
240{
241 char *buf;
242 char *pwd;
243 struct stat dotstat, pwdstat;
244 /* If PWD is accurate, use it instead of calling getwd. PWD is
245 sometimes a nicer name, and using it may avoid a fatal error if a
246 parent directory is searchable but not readable. */
7ce8671d 247 if ((pwd = egetenv ("PWD")) != 0
974b73e8
KL
248 && (IS_DIRECTORY_SEP (*pwd) || (*pwd && IS_DEVICE_SEP (pwd[1])))
249 && stat (pwd, &pwdstat) == 0
250 && stat (".", &dotstat) == 0
251 && dotstat.st_ino == pwdstat.st_ino
252 && dotstat.st_dev == pwdstat.st_dev
253#ifdef MAXPATHLEN
254 && strlen (pwd) < MAXPATHLEN
255#endif
256 )
257 {
258 buf = (char *) xmalloc (strlen (pwd) + 1);
259 if (!buf)
260 return NULL;
261 strcpy (buf, pwd);
262 }
263#ifdef HAVE_GETCWD
264 else
265 {
266 size_t buf_size = 1024;
267 buf = (char *) xmalloc (buf_size);
268 if (!buf)
269 return NULL;
270 for (;;)
271 {
272 if (getcwd (buf, buf_size) == buf)
273 break;
274 if (errno != ERANGE)
275 {
276 int tmp_errno = errno;
277 free (buf);
278 errno = tmp_errno;
279 return NULL;
280 }
281 buf_size *= 2;
282 buf = (char *) realloc (buf, buf_size);
283 if (!buf)
284 return NULL;
285 }
286 }
287#else
288 else
289 {
290 /* We need MAXPATHLEN here. */
291 buf = (char *) xmalloc (MAXPATHLEN + 1);
292 if (!buf)
293 return NULL;
294 if (getwd (buf) == NULL)
295 {
296 int tmp_errno = errno;
297 free (buf);
298 errno = tmp_errno;
299 return NULL;
300 }
301 }
302#endif
303 return buf;
304}
305#endif
306
42073bfb 307#ifdef WINDOWSNT
7ce8671d
JB
308
309#define REG_ROOT "SOFTWARE\\GNU\\Emacs"
310
311/* Retrieve an environment variable from the Emacs subkeys of the registry.
312 Return NULL if the variable was not found, or it was empty.
313 This code is based on w32_get_resource (w32.c). */
314char *
315w32_get_resource (predefined, key, type)
316 HKEY predefined;
317 char *key;
318 LPDWORD type;
319{
320 HKEY hrootkey = NULL;
321 char *result = NULL;
322 DWORD cbData;
323
324 if (RegOpenKeyEx (predefined, REG_ROOT, 0, KEY_READ, &hrootkey) == ERROR_SUCCESS)
325 {
326 if (RegQueryValueEx (hrootkey, key, NULL, NULL, NULL, &cbData) == ERROR_SUCCESS)
327 {
328 result = (char *) xmalloc (cbData);
329
bc558f3e
JB
330 if ((RegQueryValueEx (hrootkey, key, NULL, type, result, &cbData) != ERROR_SUCCESS)
331 || (*result == 0))
7ce8671d
JB
332 {
333 free (result);
334 result = NULL;
335 }
336 }
337
338 RegCloseKey (hrootkey);
339 }
340
341 return result;
342}
343
344/*
345 getenv wrapper for Windows
346
768c0c0f 347 This is needed to duplicate Emacs's behavior, which is to look for environment
7ce8671d
JB
348 variables in the registry if they don't appear in the environment.
349*/
350char *
351w32_getenv (envvar)
352 char *envvar;
353{
354 char *value;
355 DWORD dwType;
356
357 if (value = getenv (envvar))
358 /* Found in the environment. */
359 return value;
360
361 if (! (value = w32_get_resource (HKEY_CURRENT_USER, envvar, &dwType)) &&
362 ! (value = w32_get_resource (HKEY_LOCAL_MACHINE, envvar, &dwType)))
d41784ee
EZ
363 {
364 /* "w32console" is what Emacs on Windows uses for tty-type under -nw. */
365 if (strcmp (envvar, "TERM") == 0)
366 return xstrdup ("w32console");
367 /* Found neither in the environment nor in the registry. */
368 return NULL;
369 }
7ce8671d
JB
370
371 if (dwType == REG_SZ)
372 /* Registry; no need to expand. */
373 return value;
374
375 if (dwType == REG_EXPAND_SZ)
376 {
377 DWORD size;
378
379 if (size = ExpandEnvironmentStrings (value, NULL, 0))
380 {
381 char *buffer = (char *) xmalloc (size);
382 if (ExpandEnvironmentStrings (value, buffer, size))
383 {
384 /* Found and expanded. */
385 free (value);
386 return buffer;
387 }
388
389 /* Error expanding. */
390 free (buffer);
391 }
392 }
393
394 /* Not the right type, or not correctly expanded. */
395 free (value);
396 return NULL;
397}
398
ff90fbde
JR
399void
400w32_set_user_model_id ()
401{
402 HMODULE shell;
0a3472c7 403 HRESULT (WINAPI * set_user_model) (wchar_t * id);
ff90fbde
JR
404
405 /* On Windows 7 and later, we need to set the user model ID
406 to associate emacsclient launched files with Emacs frames
407 in the UI. */
408 shell = LoadLibrary("shell32.dll");
409 if (shell)
410 {
411 set_user_model
412 = (void *) GetProcAddress (shell,
413 "SetCurrentProcessExplicitAppUserModelID");
414 /* If the function is defined, then we are running on Windows 7
415 or newer, and the UI uses this to group related windows
416 together. Since emacs, runemacs, emacsclient are related, we
417 want them grouped even though the executables are different,
418 so we need to set a consistent ID between them. */
419 if (set_user_model)
420 set_user_model (L"GNU.Emacs");
421
422 FreeLibrary (shell);
423 }
424}
425
42073bfb 426int
f0384499 427w32_window_app ()
42073bfb
JB
428{
429 static int window_app = -1;
430 char szTitle[MAX_PATH];
431
432 if (window_app < 0)
dbf60b07
JR
433 {
434 /* Checking for STDOUT does not work; it's a valid handle also in
435 nonconsole apps. Testing for the console title seems to work. */
436 window_app = (GetConsoleTitleA (szTitle, MAX_PATH) == 0);
437 if (window_app)
438 InitCommonControls();
439 }
42073bfb
JB
440
441 return window_app;
442}
105faa84
DN
443
444/*
cb06b8dc 445 execvp wrapper for Windows. Quotes arguments with embedded spaces.
105faa84
DN
446
447 This is necessary due to the broken implementation of exec* routines in
448 the Microsoft libraries: they concatenate the arguments together without
449 quoting special characters, and pass the result to CreateProcess, with
450 predictably bad results. By contrast, Posix execvp passes the arguments
451 directly into the argv array of the child process.
452*/
453int
454w32_execvp (path, argv)
455 char *path;
456 char **argv;
457{
458 int i;
459
460 /* Required to allow a .BAT script as alternate editor. */
461 argv[0] = (char *) alternate_editor;
462
463 for (i = 0; argv[i]; i++)
464 if (strchr (argv[i], ' '))
465 {
466 char *quoted = alloca (strlen (argv[i]) + 3);
467 sprintf (quoted, "\"%s\"", argv[i]);
468 argv[i] = quoted;
469 }
470
471 return execvp (path, argv);
472}
473
474#undef execvp
475#define execvp w32_execvp
476
d41784ee
EZ
477/* Emulation of ttyname for Windows. */
478char *
479ttyname (int fd)
480{
481 return "CONOUT$";
482}
483
105faa84 484#endif /* WINDOWSNT */
42073bfb 485
f387c1ee
JB
486/* Display a normal or error message.
487 On Windows, use a message box if compiled as a Windows app. */
42073bfb
JB
488void
489message (int is_error, char *message, ...)
490{
c66648e0 491 char msg [2048];
42073bfb
JB
492 va_list args;
493
494 va_start (args, message);
42073bfb
JB
495 vsprintf (msg, message, args);
496 va_end (args);
497
498#ifdef WINDOWSNT
499 if (w32_window_app ())
500 {
501 if (is_error)
502 MessageBox (NULL, msg, "Emacsclient ERROR", MB_ICONERROR);
503 else
504 MessageBox (NULL, msg, "Emacsclient", MB_ICONINFORMATION);
505 }
506 else
507#endif
9219db75
JB
508 {
509 FILE *f = is_error ? stderr : stdout;
510
511 fputs (msg, f);
512 fflush (f);
513 }
42073bfb
JB
514}
515
8f9aaa0a 516/* Decode the options from argv and argc.
5212210c 517 The global variable `optind' will say how many arguments we used up. */
8f9aaa0a 518
5212210c 519void
8f9aaa0a
RS
520decode_options (argc, argv)
521 int argc;
522 char **argv;
523{
7ce8671d 524 alternate_editor = egetenv ("ALTERNATE_EDITOR");
0ea5797a 525
8f9aaa0a
RS
526 while (1)
527 {
dc1cd5f7 528 int opt = getopt_long_only (argc, argv,
b03d27bd 529#ifndef NO_SOCKETS_IN_FILE_SYSTEM
974b73e8 530 "VHnea:s:f:d:tc",
b03d27bd 531#else
974b73e8 532 "VHnea:f:d:tc",
b03d27bd 533#endif
974b73e8 534 longopts, 0);
8f9aaa0a
RS
535
536 if (opt == EOF)
537 break;
538
539 switch (opt)
540 {
541 case 0:
542 /* If getopt returns 0, then it has already processed a
543 long-named option. We should do nothing. */
544 break;
e69233c2 545
97e3214d
GM
546 case 'a':
547 alternate_editor = optarg;
548 break;
e69233c2 549
b03d27bd 550#ifndef NO_SOCKETS_IN_FILE_SYSTEM
254107e4
RS
551 case 's':
552 socket_name = optarg;
553 break;
b03d27bd 554#endif
254107e4 555
aa0b6932
JB
556 case 'f':
557 server_file = optarg;
558 break;
254107e4 559
0ea5797a
SM
560 /* We used to disallow this argument in w32, but it seems better
561 to allow it, for the occasional case where the user is
562 connecting with a w32 client to a server compiled with X11
563 support. */
30be2360
SM
564 case 'd':
565 display = optarg;
566 break;
567
8f9aaa0a
RS
568 case 'n':
569 nowait = 1;
570 break;
571
30be2360
SM
572 case 'e':
573 eval = 1;
574 break;
575
8f9aaa0a 576 case 'V':
42073bfb 577 message (FALSE, "emacsclient %s\n", VERSION);
65396510 578 exit (EXIT_SUCCESS);
8f9aaa0a 579 break;
46cec291 580
819b8f00 581 case 't':
77134727 582 tty = 1;
c1b8e896 583 current_frame = 0;
77134727
KL
584 break;
585
e5299d8d 586 case 'c':
31fa6595 587 current_frame = 0;
9628b887 588 break;
0b0d3e0b 589
0191e222
CY
590 case 'p':
591 parent_id = optarg;
592 current_frame = 0;
593 break;
594
8f9aaa0a 595 case 'H':
8f9aaa0a 596 print_help_and_exit ();
20c396e8
JB
597 break;
598
599 default:
42073bfb 600 message (TRUE, "Try `%s --help' for more information\n", progname);
65396510 601 exit (EXIT_FAILURE);
20c396e8 602 break;
8f9aaa0a
RS
603 }
604 }
9628b887 605
273b9028
CY
606 /* If the -c option is used (without -t) and no --display argument
607 is provided, try $DISPLAY.
608 Without the -c option, we used to set `display' to $DISPLAY by
609 default, but this changed the default behavior and is sometimes
610 inconvenient. So we force users to use "--display $DISPLAY" if
611 they want Emacs to connect to their current display. */
09317bf4 612 if (!current_frame && !tty && !display)
e7534fc4
AR
613 {
614 display = egetenv ("DISPLAY");
615#ifdef NS_IMPL_COCOA
616 /* Under Cocoa, we don't really use displays the same way as in X,
617 so provide a dummy. */
618 if (!display || strlen (display) == 0)
619 display = "ns";
620#endif
621 }
9997dc15 622
273b9028 623 /* A null-string display is invalid. */
0ea5797a
SM
624 if (display && strlen (display) == 0)
625 display = NULL;
626
273b9028
CY
627 /* If no display is available, new frames are tty frames. */
628 if (!current_frame && !display)
92071250 629 tty = 1;
c0f342ab 630
b8ccaf6f 631 /* --no-wait implies --current-frame on ttys when there are file
273b9028 632 arguments or expressions given. */
b8ccaf6f 633 if (nowait && tty && argc - optind > 0)
92071250 634 current_frame = 1;
802bdb3c
DN
635
636#ifdef WINDOWSNT
69157c99 637 if (alternate_editor && alternate_editor[0] == '\0')
802bdb3c
DN
638 {
639 message (TRUE, "--alternate-editor argument or ALTERNATE_EDITOR variable cannot be\n\
640an empty string");
641 exit (EXIT_FAILURE);
642 }
643#endif /* WINDOWSNT */
8f9aaa0a
RS
644}
645
974b73e8 646\f
7f3bff3e 647void
8f9aaa0a
RS
648print_help_and_exit ()
649{
c0f342ab
JB
650 /* Spaces and tabs are significant in this message; they're chosen so the
651 message aligns properly both in a tty and in a Windows message box.
652 Please try to preserve them; otherwise the output is very hard to read
653 when using emacsclientw. */
42073bfb 654 message (FALSE,
974b73e8 655 "Usage: %s [OPTIONS] FILE...\n\
30be2360
SM
656Tell the Emacs server to visit the specified files.\n\
657Every FILE can be either just a FILENAME or [+LINE[:COLUMN]] FILENAME.\n\
20c396e8 658\n\
30be2360 659The following OPTIONS are accepted:\n\
c0f342ab
JB
660-V, --version Just print version info and return\n\
661-H, --help Print this usage information message\n\
dc1cd5f7 662-nw, -t, --tty Open a new Emacs frame on the current terminal\n\
c4b858e3 663-c, --create-frame Create a new frame instead of trying to\n\
9dfda22f 664 use the current Emacs frame\n\
c0f342ab 665-e, --eval Evaluate the FILE arguments as ELisp expressions\n\
d07529f3 666-n, --no-wait Don't wait for the server to return\n\
24d5010d 667-d DISPLAY, --display=DISPLAY\n\
0191e222
CY
668 Visit the file in the given display\n\
669--parent-id=ID Open in parent window ID, via XEmbed\n"
aa0b6932 670#ifndef NO_SOCKETS_IN_FILE_SYSTEM
24d5010d 671"-s SOCKET, --socket-name=SOCKET\n\
9dfda22f 672 Set filename of the UNIX socket for communication\n"
aa0b6932 673#endif
24d5010d 674"-f SERVER, --server-file=SERVER\n\
9dfda22f 675 Set filename of the TCP authentication file\n\
24d5010d 676-a EDITOR, --alternate-editor=EDITOR\n\
9dfda22f 677 Editor to fallback to if the server is not running\n"
6133a1a9 678#ifndef WINDOWSNT
c3f995a2
JB
679" If EDITOR is the empty string, start Emacs in daemon\n\
680 mode and try connecting again\n"
6133a1a9 681#endif /* not WINDOWSNT */
c3f995a2 682"\n\
5f54cae6 683Report bugs with M-x report-emacs-bug.\n", progname);
65396510 684 exit (EXIT_SUCCESS);
8f9aaa0a 685}
5212210c 686
aa0b6932
JB
687/*
688 Try to run a different command, or --if no alternate editor is
689 defined-- exit with an errorcode.
cb06b8dc 690 Uses argv, but gets it from the global variable main_argv.
aa0b6932
JB
691*/
692void
974b73e8 693fail (void)
9002956f 694{
aa0b6932 695 if (alternate_editor)
9002956f 696 {
aa0b6932 697 int i = optind - 1;
4472aef4 698
974b73e8 699 execvp (alternate_editor, main_argv + i);
42073bfb 700 message (TRUE, "%s: error executing alternate editor \"%s\"\n",
974b73e8 701 progname, alternate_editor);
9002956f 702 }
aa0b6932 703 exit (EXIT_FAILURE);
9002956f
KL
704}
705
aa0b6932 706\f
1e7823d0 707#if !defined (HAVE_SOCKETS) || !defined (HAVE_INET_SOCKETS)
9002956f 708
aa0b6932
JB
709int
710main (argc, argv)
711 int argc;
712 char **argv;
9002956f 713{
974b73e8
KL
714 main_argv = argv;
715 progname = argv[0];
716 message (TRUE, "%s: Sorry, the Emacs server is supported only\n"
c0f342ab 717 "on systems with Berkeley sockets.\n",
aa0b6932 718 argv[0]);
974b73e8 719 fail ();
9002956f
KL
720}
721
1e7823d0 722#else /* HAVE_SOCKETS && HAVE_INET_SOCKETS */
2828d5f9 723
aa0b6932
JB
724#ifdef WINDOWSNT
725# include <winsock2.h>
2828d5f9 726#else
aa0b6932
JB
727# include <sys/types.h>
728# include <sys/socket.h>
729# include <sys/un.h>
aa0b6932
JB
730#endif
731
732#define AUTH_KEY_LENGTH 64
733#define SEND_BUFFER_SIZE 4096
734
735extern char *strerror ();
aa0b6932
JB
736
737/* Buffer to accumulate data to send in TCP connections. */
738char send_buffer[SEND_BUFFER_SIZE + 1];
739int sblen = 0; /* Fill pointer for the send buffer. */
4b7b77f6
JR
740/* Socket used to communicate with the Emacs server process. */
741HSOCKET emacs_socket = 0;
aa0b6932 742
d22b00e5
JR
743/* On Windows, the socket library was historically separate from the standard
744 C library, so errors are handled differently. */
745void
746sock_err_message (function_name)
747 char *function_name;
748{
749#ifdef WINDOWSNT
750 char* msg = NULL;
751
752 FormatMessage (FORMAT_MESSAGE_FROM_SYSTEM
753 | FORMAT_MESSAGE_ALLOCATE_BUFFER
754 | FORMAT_MESSAGE_ARGUMENT_ARRAY,
755 NULL, WSAGetLastError (), 0, (LPTSTR)&msg, 0, NULL);
756
757 message (TRUE, "%s: %s: %s\n", progname, function_name, msg);
758
759 LocalFree (msg);
760#else
761 message (TRUE, "%s: %s: %s\n", progname, function_name, strerror (errno));
762#endif
763}
764
765
aa0b6932
JB
766/* Let's send the data to Emacs when either
767 - the data ends in "\n", or
768 - the buffer is full (but this shouldn't happen)
769 Otherwise, we just accumulate it. */
b03d27bd
JB
770void
771send_to_emacs (s, data)
aa0b6932
JB
772 HSOCKET s;
773 char *data;
774{
775 while (data)
2828d5f9 776 {
aa0b6932
JB
777 int dlen = strlen (data);
778 if (dlen + sblen >= SEND_BUFFER_SIZE)
779 {
780 int part = SEND_BUFFER_SIZE - sblen;
781 strncpy (&send_buffer[sblen], data, part);
782 data += part;
783 sblen = SEND_BUFFER_SIZE;
784 }
785 else if (dlen)
786 {
787 strcpy (&send_buffer[sblen], data);
788 data = NULL;
789 sblen += dlen;
790 }
791 else
792 break;
793
794 if (sblen == SEND_BUFFER_SIZE
795 || (sblen > 0 && send_buffer[sblen-1] == '\n'))
796 {
797 int sent = send (s, send_buffer, sblen, 0);
798 if (sent != sblen)
799 strcpy (send_buffer, &send_buffer[sent]);
800 sblen -= sent;
801 }
2828d5f9 802 }
2828d5f9 803}
2828d5f9
KL
804
805\f
0b0d3e0b 806/* In STR, insert a & before each &, each space, each newline, and
a4cf2096 807 any initial -. Change spaces to underscores, too, so that the
0b0d3e0b
KL
808 return value never contains a space.
809
810 Does not change the string. Outputs the result to STREAM. */
87209357 811void
974b73e8 812quote_argument (s, str)
aa0b6932 813 HSOCKET s;
0b0d3e0b 814 char *str;
5212210c 815{
9002956f 816 char *copy = (char *) xmalloc (strlen (str) * 2 + 1);
5212210c
RS
817 char *p, *q;
818
0b0d3e0b 819 p = str;
5212210c
RS
820 q = copy;
821 while (*p)
822 {
823 if (*p == ' ')
824 {
f1db6a73 825 *q++ = '&';
5212210c
RS
826 *q++ = '_';
827 p++;
828 }
3cf8c6aa
SM
829 else if (*p == '\n')
830 {
831 *q++ = '&';
832 *q++ = 'n';
833 p++;
834 }
5212210c
RS
835 else
836 {
0b0d3e0b 837 if (*p == '&' || (*p == '-' && p == str))
f1db6a73 838 *q++ = '&';
5212210c
RS
839 *q++ = *p++;
840 }
841 }
f1db6a73 842 *q++ = 0;
5212210c 843
486ba65f 844 send_to_emacs (s, copy);
87209357
EZ
845
846 free (copy);
5212210c 847}
0c76956f 848
0b0d3e0b
KL
849
850/* The inverse of quote_argument. Removes quoting in string STR by
851 modifying the string in place. Returns STR. */
852
853char *
854unquote_argument (str)
855 char *str;
856{
857 char *p, *q;
858
859 if (! str)
860 return str;
861
862 p = str;
863 q = str;
864 while (*p)
865 {
866 if (*p == '&')
867 {
868 p++;
869 if (*p == '&')
870 *p = '&';
871 else if (*p == '_')
872 *p = ' ';
873 else if (*p == 'n')
874 *p = '\n';
875 else if (*p == '-')
876 *p = '-';
877 }
878 *q++ = *p++;
879 }
880 *q = 0;
881 return str;
882}
883
8f9aaa0a 884\f
b03d27bd
JB
885int
886file_name_absolute_p (filename)
887 const unsigned char *filename;
888{
889 /* Sanity check, it shouldn't happen. */
890 if (! filename) return FALSE;
891
892 /* /xxx is always an absolute path. */
893 if (filename[0] == '/') return TRUE;
894
895 /* Empty filenames (which shouldn't happen) are relative. */
896 if (filename[0] == '\0') return FALSE;
897
898#ifdef WINDOWSNT
71b8f735 899 /* X:\xxx is always absolute. */
5f7a4874 900 if (isalpha (filename[0])
cb0297bb 901 && filename[1] == ':' && (filename[2] == '\\' || filename[2] == '/'))
b03d27bd
JB
902 return TRUE;
903
904 /* Both \xxx and \\xxx\yyy are absolute. */
905 if (filename[0] == '\\') return TRUE;
906#endif
907
908 return FALSE;
909}
910
aa0b6932 911#ifdef WINDOWSNT
f0384499 912/* Wrapper to make WSACleanup a cdecl, as required by atexit. */
b03d27bd
JB
913void
914__cdecl close_winsock ()
aa0b6932
JB
915{
916 WSACleanup ();
917}
0c76956f 918
b03d27bd
JB
919/* Initialize the WinSock2 library. */
920void
921initialize_sockets ()
0c76956f 922{
aa0b6932
JB
923 WSADATA wsaData;
924
aa0b6932
JB
925 if (WSAStartup (MAKEWORD (2, 0), &wsaData))
926 {
78da39c6 927 message (TRUE, "%s: error initializing WinSock2\n", progname);
aa0b6932
JB
928 exit (EXIT_FAILURE);
929 }
930
931 atexit (close_winsock);
0c76956f 932}
e35fc962 933#endif /* WINDOWSNT */
974b73e8 934
8f9aaa0a 935\f
97e3214d 936/*
aa0b6932 937 * Read the information needed to set up a TCP comm channel with
434a6c5d 938 * the Emacs server: host, port, pid and authentication string.
0e0dced5 939 */
b03d27bd
JB
940int
941get_server_config (server, authentication)
aa0b6932
JB
942 struct sockaddr_in *server;
943 char *authentication;
97e3214d 944{
aa0b6932
JB
945 char dotted[32];
946 char *port;
434a6c5d 947 char *pid;
b03d27bd 948 FILE *config = NULL;
aa0b6932 949
b03d27bd
JB
950 if (file_name_absolute_p (server_file))
951 config = fopen (server_file, "rb");
952 else
97e3214d 953 {
7ce8671d 954 char *home = egetenv ("HOME");
88b46d84 955
aa0b6932
JB
956 if (home)
957 {
bc558f3e
JB
958 char *path = alloca (strlen (home) + strlen (server_file)
959 + EXTRA_SPACE);
aa0b6932
JB
960 sprintf (path, "%s/.emacs.d/server/%s", home, server_file);
961 config = fopen (path, "rb");
962 }
88b46d84 963#ifdef WINDOWSNT
7ce8671d 964 if (!config && (home = egetenv ("APPDATA")))
88b46d84 965 {
bc558f3e
JB
966 char *path = alloca (strlen (home) + strlen (server_file)
967 + EXTRA_SPACE);
88b46d84
JB
968 sprintf (path, "%s/.emacs.d/server/%s", home, server_file);
969 config = fopen (path, "rb");
970 }
971#endif
aa0b6932
JB
972 }
973
974 if (! config)
975 return FALSE;
976
977 if (fgets (dotted, sizeof dotted, config)
434a6c5d
JB
978 && (port = strchr (dotted, ':'))
979 && (pid = strchr (port, ' ')))
aa0b6932
JB
980 {
981 *port++ = '\0';
434a6c5d 982 *pid++ = '\0';
97e3214d
GM
983 }
984 else
985 {
78da39c6 986 message (TRUE, "%s: invalid configuration info\n", progname);
65396510 987 exit (EXIT_FAILURE);
97e3214d 988 }
97e3214d 989
aa0b6932
JB
990 server->sin_family = AF_INET;
991 server->sin_addr.s_addr = inet_addr (dotted);
992 server->sin_port = htons (atoi (port));
97e3214d 993
aa0b6932
JB
994 if (! fread (authentication, AUTH_KEY_LENGTH, 1, config))
995 {
78da39c6 996 message (TRUE, "%s: cannot read authentication info\n", progname);
aa0b6932
JB
997 exit (EXIT_FAILURE);
998 }
46cec291 999
aa0b6932 1000 fclose (config);
97e3214d 1001
c66648e0 1002 emacs_pid = atoi (pid);
434a6c5d 1003
aa0b6932 1004 return TRUE;
97e3214d
GM
1005}
1006
aa0b6932
JB
1007HSOCKET
1008set_tcp_socket ()
1009{
1010 HSOCKET s;
1011 struct sockaddr_in server;
aa0b6932
JB
1012 struct linger l_arg = {1, 1};
1013 char auth_string[AUTH_KEY_LENGTH + 1];
9628b887 1014
aa0b6932
JB
1015 if (! get_server_config (&server, auth_string))
1016 return INVALID_SOCKET;
1017
b03d27bd 1018 if (server.sin_addr.s_addr != inet_addr ("127.0.0.1"))
9219db75 1019 message (FALSE, "%s: connected to remote socket at %s\n",
b03d27bd
JB
1020 progname, inet_ntoa (server.sin_addr));
1021
aa0b6932
JB
1022 /*
1023 * Open up an AF_INET socket
1024 */
1025 if ((s = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0)
1026 {
d22b00e5 1027 sock_err_message ("socket");
aa0b6932
JB
1028 return INVALID_SOCKET;
1029 }
1030
1031 /*
1032 * Set up the socket
1033 */
1034 if (connect (s, (struct sockaddr *) &server, sizeof server) < 0)
1035 {
d22b00e5 1036 sock_err_message ("connect");
aa0b6932
JB
1037 return INVALID_SOCKET;
1038 }
1039
aa0b6932
JB
1040 setsockopt (s, SOL_SOCKET, SO_LINGER, (char *) &l_arg, sizeof l_arg);
1041
1042 /*
1043 * Send the authentication
1044 */
1045 auth_string[AUTH_KEY_LENGTH] = '\0';
1046
486ba65f
JR
1047 send_to_emacs (s, "-auth ");
1048 send_to_emacs (s, auth_string);
5ab73228 1049 send_to_emacs (s, " ");
aa0b6932
JB
1050
1051 return s;
1052}
1053
b2ff54a0
JR
1054
1055/* Returns 1 if PREFIX is a prefix of STRING. */
1056static int
1057strprefix (char *prefix, char *string)
1058{
cb06b8dc 1059 return !strncmp (prefix, string, strlen (prefix));
b2ff54a0
JR
1060}
1061
a336ee5b
CY
1062/* Get tty name and type. If successful, return the type in TTY_TYPE
1063 and the name in TTY_NAME, and return 1. Otherwise, fail if NOABORT
1064 is zero, or return 0 if NOABORT is non-zero. */
1065
1066int
1067find_tty (char **tty_type, char **tty_name, int noabort)
1068{
1069 char *type = egetenv ("TERM");
1070 char *name = ttyname (fileno (stdout));
1071
1072 if (!name)
1073 {
1074 if (noabort)
1075 return 0;
1076 else
1077 {
1078 message (TRUE, "%s: could not get terminal name\n", progname);
1079 fail ();
1080 }
1081 }
1082
1083 if (!type)
1084 {
1085 if (noabort)
1086 return 0;
1087 else
1088 {
1089 message (TRUE, "%s: please set the TERM variable to your terminal type\n",
1090 progname);
1091 fail ();
1092 }
1093 }
1094
1095 if (strcmp (type, "eterm") == 0)
1096 {
1097 if (noabort)
1098 return 0;
1099 else
1100 {
1101 /* This causes nasty, MULTI_KBOARD-related input lockouts. */
1102 message (TRUE, "%s: opening a frame in an Emacs term buffer"
1103 " is not supported\n", progname);
1104 fail ();
1105 }
1106 }
1107
1108 *tty_name = name;
1109 *tty_type = type;
1110 return 1;
1111}
1112
b2ff54a0 1113
aa0b6932 1114#if !defined (NO_SOCKETS_IN_FILE_SYSTEM)
46cec291 1115
9f637eea
GM
1116/* Three possibilities:
1117 2 - can't be `stat'ed (sets errno)
1118 1 - isn't owned by us
1119 0 - success: none of the above */
1120
1121static int
1122socket_status (socket_name)
1123 char *socket_name;
1124{
1125 struct stat statbfr;
1126
1127 if (stat (socket_name, &statbfr) == -1)
1128 return 2;
1129
1130 if (statbfr.st_uid != geteuid ())
1131 return 1;
0b0d3e0b 1132
9f637eea
GM
1133 return 0;
1134}
1135
974b73e8 1136\f
da8e1115
KL
1137/* A signal handler that passes the signal to the Emacs process.
1138 Useful for SIGWINCH. */
1139
9628b887 1140SIGTYPE
428a555e 1141pass_signal_to_emacs (int signalnum)
9628b887
KL
1142{
1143 int old_errno = errno;
1144
9f729af5 1145 if (emacs_pid)
428a555e 1146 kill (emacs_pid, signalnum);
9f729af5 1147
428a555e 1148 signal (signalnum, pass_signal_to_emacs);
9f729af5
KL
1149 errno = old_errno;
1150}
1151
0b0d3e0b
KL
1152/* Signal handler for SIGCONT; notify the Emacs process that it can
1153 now resume our tty frame. */
1154
1155SIGTYPE
1156handle_sigcont (int signalnum)
1157{
1158 int old_errno = errno;
1159
1160 if (tcgetpgrp (1) == getpgrp ())
1161 {
1162 /* We are in the foreground. */
486ba65f 1163 send_to_emacs (emacs_socket, "-resume \n");
0b0d3e0b
KL
1164 }
1165 else
1166 {
1167 /* We are in the background; cancel the continue. */
1168 kill (getpid (), SIGSTOP);
1169 }
c6c53c3e
KL
1170
1171 signal (signalnum, handle_sigcont);
0b0d3e0b
KL
1172 errno = old_errno;
1173}
1174
1175/* Signal handler for SIGTSTP; notify the Emacs process that we are
1176 going to sleep. Normally the suspend is initiated by Emacs via
1177 server-handle-suspend-tty, but if the server gets out of sync with
1178 reality, we may get a SIGTSTP on C-z. Handling this signal and
1179 notifying Emacs about it should get things under control again. */
1180
1181SIGTYPE
1182handle_sigtstp (int signalnum)
1183{
1184 int old_errno = errno;
1185 sigset_t set;
c0f342ab 1186
90843190 1187 if (emacs_socket)
486ba65f 1188 send_to_emacs (emacs_socket, "-suspend \n");
0b0d3e0b 1189
5ab73228 1190 /* Unblock this signal and call the default handler by temporarily
0b0d3e0b
KL
1191 changing the handler and resignalling. */
1192 sigprocmask (SIG_BLOCK, NULL, &set);
1193 sigdelset (&set, signalnum);
1194 signal (signalnum, SIG_DFL);
1195 kill (getpid (), signalnum);
1196 sigprocmask (SIG_SETMASK, &set, NULL); /* Let's the above signal through. */
1197 signal (signalnum, handle_sigtstp);
1198
1199 errno = old_errno;
1200}
273b9028
CY
1201
1202
da8e1115 1203/* Set up signal handlers before opening a frame on the current tty. */
0b0d3e0b 1204
4d553a13
KL
1205void
1206init_signals (void)
9628b887
KL
1207{
1208 /* Set up signal handlers. */
428a555e 1209 signal (SIGWINCH, pass_signal_to_emacs);
4ca927b4
KL
1210
1211 /* Don't pass SIGINT and SIGQUIT to Emacs, because it has no way of
1212 deciding which terminal the signal came from. C-g is now a
1213 normal input event on secondary terminals. */
1214#if 0
428a555e
KL
1215 signal (SIGINT, pass_signal_to_emacs);
1216 signal (SIGQUIT, pass_signal_to_emacs);
4ca927b4 1217#endif
0b0d3e0b
KL
1218
1219 signal (SIGCONT, handle_sigcont);
1220 signal (SIGTSTP, handle_sigtstp);
1221 signal (SIGTTOU, handle_sigtstp);
9628b887
KL
1222}
1223
46cec291 1224
aa0b6932
JB
1225HSOCKET
1226set_local_socket ()
46cec291 1227{
aa0b6932 1228 HSOCKET s;
46cec291 1229 struct sockaddr_un server;
46cec291 1230
e69233c2 1231 /*
46cec291
RS
1232 * Open up an AF_UNIX socket in this person's home directory
1233 */
1234
1235 if ((s = socket (AF_UNIX, SOCK_STREAM, 0)) < 0)
1236 {
42073bfb 1237 message (TRUE, "%s: socket: %s\n", progname, strerror (errno));
aa0b6932 1238 return INVALID_SOCKET;
46cec291 1239 }
e69233c2 1240
46cec291 1241 server.sun_family = AF_UNIX;
c5fee545 1242
c5fee545 1243 {
9f637eea 1244 int sock_status = 0;
5c9659d3 1245 int default_sock = !socket_name;
b80bf66e 1246 int saved_errno = 0;
0734b0d0 1247 char *server_name = "server";
f77b11a0 1248 char *tmpdir;
0b0d3e0b 1249
0734b0d0
SM
1250 if (socket_name && !index (socket_name, '/') && !index (socket_name, '\\'))
1251 { /* socket_name is a file name component. */
d3a6748c
KL
1252 server_name = socket_name;
1253 socket_name = NULL;
1254 default_sock = 1; /* Try both UIDs. */
0734b0d0 1255 }
efb859b4 1256
5c9659d3 1257 if (default_sock)
254107e4 1258 {
f77b11a0
JB
1259 tmpdir = egetenv ("TMPDIR");
1260 if (!tmpdir)
1261 tmpdir = "/tmp";
bc558f3e
JB
1262 socket_name = alloca (strlen (tmpdir) + strlen (server_name)
1263 + EXTRA_SPACE);
f77b11a0
JB
1264 sprintf (socket_name, "%s/emacs%d/%s",
1265 tmpdir, (int) geteuid (), server_name);
254107e4
RS
1266 }
1267
1268 if (strlen (socket_name) < sizeof (server.sun_path))
1269 strcpy (server.sun_path, socket_name);
1270 else
819b8f00 1271 {
78da39c6 1272 message (TRUE, "%s: socket-name %s too long\n",
974b73e8 1273 progname, socket_name);
819b8f00
KL
1274 fail ();
1275 }
efb859b4 1276
9f637eea
GM
1277 /* See if the socket exists, and if it's owned by us. */
1278 sock_status = socket_status (server.sun_path);
152b6e83 1279 saved_errno = errno;
5c9659d3 1280 if (sock_status && default_sock)
efb859b4 1281 {
9f637eea
GM
1282 /* Failing that, see if LOGNAME or USER exist and differ from
1283 our euid. If so, look for a socket based on the UID
1284 associated with the name. This is reminiscent of the logic
1285 that init_editfns uses to set the global Vuser_full_name. */
e69233c2 1286
7ce8671d 1287 char *user_name = (char *) egetenv ("LOGNAME");
293f9f2a 1288
9f637eea 1289 if (!user_name)
7ce8671d 1290 user_name = (char *) egetenv ("USER");
e69233c2 1291
9f637eea
GM
1292 if (user_name)
1293 {
1294 struct passwd *pw = getpwnam (user_name);
293f9f2a 1295
9f637eea
GM
1296 if (pw && (pw->pw_uid != geteuid ()))
1297 {
1298 /* We're running under su, apparently. */
bc558f3e
JB
1299 socket_name = alloca (strlen (tmpdir) + strlen (server_name)
1300 + EXTRA_SPACE);
f77b11a0
JB
1301 sprintf (socket_name, "%s/emacs%d/%s",
1302 tmpdir, (int) pw->pw_uid, server_name);
5c9659d3
SM
1303
1304 if (strlen (socket_name) < sizeof (server.sun_path))
1305 strcpy (server.sun_path, socket_name);
1306 else
1307 {
78da39c6 1308 message (TRUE, "%s: socket-name %s too long\n",
aa0b6932 1309 progname, socket_name);
65396510 1310 exit (EXIT_FAILURE);
5c9659d3
SM
1311 }
1312
9f637eea 1313 sock_status = socket_status (server.sun_path);
b80bf66e 1314 saved_errno = errno;
9f637eea 1315 }
293f9f2a
RS
1316 else
1317 errno = saved_errno;
9f637eea 1318 }
efb859b4 1319 }
e69233c2 1320
aa0b6932
JB
1321 switch (sock_status)
1322 {
1323 case 1:
974b73e8
KL
1324 /* There's a socket, but it isn't owned by us. This is OK if
1325 we are root. */
1326 if (0 != geteuid ())
1327 {
1328 message (TRUE, "%s: Invalid socket owner\n", progname);
aa0b6932 1329 return INVALID_SOCKET;
974b73e8
KL
1330 }
1331 break;
aa0b6932
JB
1332
1333 case 2:
974b73e8
KL
1334 /* `stat' failed */
1335 if (saved_errno == ENOENT)
1336 message (TRUE,
1337 "%s: can't find socket; have you started the server?\n\
45adde32 1338To start the server in Emacs, type \"M-x server-start\".\n",
aa0b6932 1339 progname);
974b73e8
KL
1340 else
1341 message (TRUE, "%s: can't stat %s: %s\n",
aa0b6932 1342 progname, server.sun_path, strerror (saved_errno));
974b73e8 1343 return INVALID_SOCKET;
aa0b6932 1344 }
efb859b4 1345 }
46cec291 1346
4e23f2ba
JB
1347 if (connect (s, (struct sockaddr *) &server, strlen (server.sun_path) + 2)
1348 < 0)
46cec291 1349 {
42073bfb 1350 message (TRUE, "%s: connect: %s\n", progname, strerror (errno));
aa0b6932 1351 return INVALID_SOCKET;
46cec291 1352 }
23a7488d 1353
aa0b6932
JB
1354 return s;
1355}
1356#endif /* ! NO_SOCKETS_IN_FILE_SYSTEM */
1357
1358HSOCKET
636b507b 1359set_socket (int no_exit_if_error)
aa0b6932 1360{
b03d27bd 1361 HSOCKET s;
c0f342ab 1362
b03d27bd 1363 INITIALIZE ();
c0f342ab 1364
aa0b6932 1365#ifndef NO_SOCKETS_IN_FILE_SYSTEM
b03d27bd
JB
1366 /* Explicit --socket-name argument. */
1367 if (socket_name)
46cec291 1368 {
b03d27bd 1369 s = set_local_socket ();
636b507b 1370 if ((s != INVALID_SOCKET) || no_exit_if_error)
974b73e8 1371 return s;
355a326e 1372 message (TRUE, "%s: error accessing socket \"%s\"\n",
974b73e8 1373 progname, socket_name);
b03d27bd 1374 exit (EXIT_FAILURE);
46cec291 1375 }
b03d27bd
JB
1376#endif
1377
1378 /* Explicit --server-file arg or EMACS_SERVER_FILE variable. */
1379 if (!server_file)
7ce8671d 1380 server_file = egetenv ("EMACS_SERVER_FILE");
46cec291 1381
b03d27bd 1382 if (server_file)
23a7488d 1383 {
b03d27bd 1384 s = set_tcp_socket ();
636b507b 1385 if ((s != INVALID_SOCKET) || no_exit_if_error)
974b73e8 1386 return s;
c0f342ab 1387
78da39c6 1388 message (TRUE, "%s: error accessing server file \"%s\"\n",
974b73e8 1389 progname, server_file);
b03d27bd 1390 exit (EXIT_FAILURE);
23a7488d 1391 }
c0f342ab 1392
b03d27bd
JB
1393#ifndef NO_SOCKETS_IN_FILE_SYSTEM
1394 /* Implicit local socket. */
1395 s = set_local_socket ();
1396 if (s != INVALID_SOCKET)
1397 return s;
1398#endif
23a7488d 1399
b03d27bd
JB
1400 /* Implicit server file. */
1401 server_file = "server";
1402 s = set_tcp_socket ();
636b507b 1403 if ((s != INVALID_SOCKET) || no_exit_if_error)
b03d27bd
JB
1404 return s;
1405
1406 /* No implicit or explicit socket, and no alternate editor. */
42073bfb 1407 message (TRUE, "%s: No socket or alternate editor. Please use:\n\n"
b03d27bd
JB
1408#ifndef NO_SOCKETS_IN_FILE_SYSTEM
1409"\t--socket-name\n"
ee6a193c 1410#endif
b03d27bd
JB
1411"\t--server-file (or environment variable EMACS_SERVER_FILE)\n\
1412\t--alternate-editor (or environment variable ALTERNATE_EDITOR)\n",
1413 progname);
1414 exit (EXIT_FAILURE);
aa0b6932 1415}
46cec291 1416
0e0dced5
JB
1417#ifdef WINDOWSNT
1418FARPROC set_fg; /* Pointer to AllowSetForegroundWindow. */
1419FARPROC get_wc; /* Pointer to RealGetWindowClassA. */
1420
1421BOOL CALLBACK
1422w32_find_emacs_process (hWnd, lParam)
1423 HWND hWnd;
1424 LPARAM lParam;
1425{
1426 DWORD pid;
1427 char class[6];
1428
1429 /* Reject any window not of class "Emacs". */
1430 if (! get_wc (hWnd, class, sizeof (class))
1431 || strcmp (class, "Emacs"))
1432 return TRUE;
1433
1434 /* We only need the process id, not the thread id. */
1435 (void) GetWindowThreadProcessId (hWnd, &pid);
1436
1437 /* Not the one we're looking for. */
1438 if (pid != (DWORD) emacs_pid) return TRUE;
1439
1440 /* OK, let's raise it. */
1441 set_fg (emacs_pid);
1442
1443 /* Stop enumeration. */
1444 return FALSE;
1445}
1446
1447/*
1448 * Search for a window of class "Emacs" and owned by a process with
1449 * process id = emacs_pid. If found, allow it to grab the focus.
1450 */
1451void
1452w32_give_focus ()
1453{
ff90fbde 1454 HANDLE user32;
0e0dced5 1455
71b8f735 1456 /* It shouldn't happen when dealing with TCP sockets. */
0e0dced5
JB
1457 if (!emacs_pid) return;
1458
ff90fbde
JR
1459 user32 = GetModuleHandle ("user32.dll");
1460
1461 if (!user32)
1462 return;
0e0dced5
JB
1463
1464 /* Modern Windows restrict which processes can set the foreground window.
1465 emacsclient can allow Emacs to grab the focus by calling the function
1466 AllowSetForegroundWindow. Unfortunately, older Windows (W95, W98 and
1467 NT) lack this function, so we have to check its availability. */
ff90fbde
JR
1468 if ((set_fg = GetProcAddress (user32, "AllowSetForegroundWindow"))
1469 && (get_wc = GetProcAddress (user32, "RealGetWindowClassA")))
0e0dced5 1470 EnumWindows (w32_find_emacs_process, (LPARAM) 0);
0e0dced5
JB
1471}
1472#endif
1473
636b507b
DN
1474/* Start the emacs daemon and try to connect to it. */
1475
1476void
1477start_daemon_and_retry_set_socket (void)
1478{
802bdb3c 1479#ifndef WINDOWSNT
636b507b
DN
1480 pid_t dpid;
1481 int status;
636b507b
DN
1482
1483 dpid = fork ();
1484
1485 if (dpid > 0)
1486 {
fd95644b
DN
1487 pid_t w;
1488 w = waitpid (dpid, &status, WUNTRACED | WCONTINUED);
636b507b 1489
fd95644b
DN
1490 if ((w == -1) || !WIFEXITED (status) || WEXITSTATUS(status))
1491 {
1492 message (TRUE, "Error: Could not start the Emacs daemon\n");
1493 exit (EXIT_FAILURE);
1494 }
1495
1496 /* Try connecting, the daemon should have started by now. */
1497 message (TRUE, "Emacs daemon should have started, trying to connect again\n");
636b507b 1498 if ((emacs_socket = set_socket (1)) == INVALID_SOCKET)
fd95644b
DN
1499 {
1500 message (TRUE, "Error: Cannot connect even after starting the Emacs daemon\n");
1501 exit (EXIT_FAILURE);
1502 }
636b507b
DN
1503 }
1504 else if (dpid < 0)
1505 {
fd95644b 1506 fprintf (stderr, "Error: Cannot fork!\n");
636b507b
DN
1507 exit (1);
1508 }
1509 else
1510 {
1511 char *d_argv[] = {"emacs", "--daemon", 0 };
1512 if (socket_name != NULL)
1513 {
1514 /* Pass --daemon=socket_name as argument. */
1515 char *deq = "--daemon=";
1516 char *daemon_arg = alloca (strlen (deq)
1517 + strlen (socket_name) + 1);
1518 strcpy (daemon_arg, deq);
1519 strcat (daemon_arg, socket_name);
1520 d_argv[1] = daemon_arg;
1521 }
1522 execvp ("emacs", d_argv);
1523 message (TRUE, "%s: error starting emacs daemon\n", progname);
1524 }
802bdb3c 1525#endif /* WINDOWSNT */
636b507b
DN
1526}
1527
aa0b6932
JB
1528int
1529main (argc, argv)
1530 int argc;
1531 char **argv;
1532{
aa0b6932 1533 int i, rl, needlf = 0;
974b73e8 1534 char *cwd, *str;
aa0b6932 1535 char string[BUFSIZ+1];
802bdb3c 1536 int null_socket_name, null_server_file, start_daemon_if_needed;
aa0b6932 1537
974b73e8 1538 main_argv = argv;
aa0b6932
JB
1539 progname = argv[0];
1540
ff90fbde
JR
1541#ifdef WINDOWSNT
1542 /* On Windows 7 and later, we need to explicitly associate emacsclient
1543 with emacs so the UI behaves sensibly. */
1544 w32_set_user_model_id ();
1545#endif
1546
aa0b6932
JB
1547 /* Process options. */
1548 decode_options (argc, argv);
1549
273b9028 1550 if ((argc - optind < 1) && !eval && current_frame)
23a7488d 1551 {
974b73e8
KL
1552 message (TRUE, "%s: file name or argument required\n"
1553 "Try `%s --help' for more information\n",
1554 progname, progname);
aa0b6932 1555 exit (EXIT_FAILURE);
23a7488d
RS
1556 }
1557
636b507b
DN
1558 /* If alternate_editor is the empty string, start the emacs daemon
1559 in case of failure to connect. */
1560 start_daemon_if_needed = (alternate_editor
1561 && (alternate_editor[0] == '\0'));
1562 if (start_daemon_if_needed)
1563 {
1564 /* set_socket changes the values for socket_name and
1565 server_file, we need to reset them, if they were NULL before
1566 for the second call to set_socket. */
1567 null_socket_name = (socket_name == NULL);
1568 null_server_file = (server_file == NULL);
1569 }
aa0b6932 1570
636b507b
DN
1571 if ((emacs_socket = set_socket (alternate_editor
1572 || start_daemon_if_needed)) == INVALID_SOCKET)
1573 if (start_daemon_if_needed)
1574 {
1575 /* Reset socket_name and server_file if they were NULL
1576 before the set_socket call. */
1577 if (null_socket_name)
1578 socket_name = NULL;
1579 if (null_server_file)
1580 server_file = NULL;
1581
1582 start_daemon_and_retry_set_socket ();
1583 }
1584 else
1585 fail ();
974b73e8
KL
1586
1587 cwd = get_current_dir_name ();
46cec291
RS
1588 if (cwd == 0)
1589 {
1590 /* getwd puts message in STRING if it fails. */
974b73e8
KL
1591 message (TRUE, "%s: %s\n", progname,
1592 "Cannot get current working directory");
819b8f00 1593 fail ();
46cec291
RS
1594 }
1595
c66648e0 1596#ifdef WINDOWSNT
0e0dced5 1597 w32_give_focus ();
c66648e0
JB
1598#endif
1599
273b9028 1600 /* Send over our environment and current directory. */
59e085e0
KL
1601 if (!current_frame)
1602 {
1603 extern char **environ;
1604 int i;
1605 for (i = 0; environ[i]; i++)
1606 {
1607 char *name = xstrdup (environ[i]);
1608 char *value = strchr (name, '=');
486ba65f
JR
1609 send_to_emacs (emacs_socket, "-env ");
1610 quote_argument (emacs_socket, environ[i]);
1611 send_to_emacs (emacs_socket, " ");
59e085e0 1612 }
2828d5f9 1613 }
ba528748
SM
1614 send_to_emacs (emacs_socket, "-dir ");
1615 quote_argument (emacs_socket, cwd);
1616 send_to_emacs (emacs_socket, "/");
1617 send_to_emacs (emacs_socket, " ");
2828d5f9 1618
6afdd335 1619 retry:
5212210c 1620 if (nowait)
486ba65f 1621 send_to_emacs (emacs_socket, "-nowait ");
292d74a3 1622
92071250 1623 if (current_frame)
486ba65f 1624 send_to_emacs (emacs_socket, "-current-frame ");
c0f342ab 1625
30be2360 1626 if (display)
87209357 1627 {
486ba65f
JR
1628 send_to_emacs (emacs_socket, "-display ");
1629 quote_argument (emacs_socket, display);
1630 send_to_emacs (emacs_socket, " ");
87209357 1631 }
30be2360 1632
0191e222
CY
1633 if (parent_id)
1634 {
1635 send_to_emacs (emacs_socket, "-parent-id ");
1636 quote_argument (emacs_socket, parent_id);
1637 send_to_emacs (emacs_socket, " ");
1638 }
1639
8536c0f5
CY
1640 /* If using the current frame, send tty information to Emacs anyway.
1641 In daemon mode, Emacs may need to occupy this tty if no other
1642 frame is available. */
322ca650 1643 if (tty || (current_frame && !eval))
9628b887 1644 {
273b9028 1645 char *tty_type, *tty_name;
0b0d3e0b 1646
273b9028
CY
1647 if (find_tty (&tty_type, &tty_name, !tty))
1648 {
b2ff54a0 1649#if !defined (NO_SOCKETS_IN_FILE_SYSTEM)
273b9028 1650 init_signals ();
b2ff54a0 1651#endif
273b9028
CY
1652 send_to_emacs (emacs_socket, "-tty ");
1653 quote_argument (emacs_socket, tty_name);
1654 send_to_emacs (emacs_socket, " ");
1655 quote_argument (emacs_socket, tty_type);
1656 send_to_emacs (emacs_socket, " ");
1657 }
9628b887 1658 }
77134727 1659
273b9028 1660 if (!current_frame && !tty)
486ba65f 1661 send_to_emacs (emacs_socket, "-window-system ");
0b0d3e0b 1662
87209357 1663 if ((argc - optind > 0))
5212210c 1664 {
87209357 1665 for (i = optind; i < argc; i++)
46cec291 1666 {
0b0d3e0b 1667
87209357 1668 if (eval)
0b0d3e0b 1669 {
974b73e8 1670 /* Don't prepend cwd or anything like that. */
486ba65f
JR
1671 send_to_emacs (emacs_socket, "-eval ");
1672 quote_argument (emacs_socket, argv[i]);
1673 send_to_emacs (emacs_socket, " ");
0b0d3e0b
KL
1674 continue;
1675 }
1676
1677 if (*argv[i] == '+')
1678 {
87209357
EZ
1679 char *p = argv[i] + 1;
1680 while (isdigit ((unsigned char) *p) || *p == ':') p++;
0b0d3e0b
KL
1681 if (*p == 0)
1682 {
486ba65f
JR
1683 send_to_emacs (emacs_socket, "-position ");
1684 quote_argument (emacs_socket, argv[i]);
1685 send_to_emacs (emacs_socket, " ");
0b0d3e0b
KL
1686 continue;
1687 }
0b0d3e0b 1688 }
6cde1b21
JB
1689#ifdef WINDOWSNT
1690 else if (! file_name_absolute_p (argv[i])
1691 && (isalpha (argv[i][0]) && argv[i][1] == ':'))
1692 /* Windows can have a different default directory for each
1693 drive, so the cwd passed via "-dir" is not sufficient
1694 to account for that.
1695 If the user uses <drive>:<relpath>, we hence need to be
1696 careful to expand <relpath> with the default directory
1697 corresponding to <drive>. */
1698 {
1699 char *filename = (char *) xmalloc (MAX_PATH);
1700 DWORD size;
1701
1702 size = GetFullPathName (argv[i], MAX_PATH, filename, NULL);
1703 if (size > 0 && size < MAX_PATH)
1704 argv[i] = filename;
1705 else
1706 free (filename);
1707 }
1708#endif
0b0d3e0b 1709
486ba65f 1710 send_to_emacs (emacs_socket, "-file ");
486ba65f
JR
1711 quote_argument (emacs_socket, argv[i]);
1712 send_to_emacs (emacs_socket, " ");
0b0d3e0b 1713 }
46cec291 1714 }
273b9028 1715 else if (eval)
87209357 1716 {
273b9028
CY
1717 /* Read expressions interactively. */
1718 while ((str = fgets (string, BUFSIZ, stdin)))
1719 {
1720 send_to_emacs (emacs_socket, "-eval ");
1721 quote_argument (emacs_socket, str);
1722 }
1723 send_to_emacs (emacs_socket, " ");
87209357 1724 }
0b0d3e0b 1725
486ba65f 1726 send_to_emacs (emacs_socket, "\n");
46cec291 1727
fc2040c0
KL
1728 /* Wait for an answer. */
1729 if (!eval && !tty && !nowait)
30be2360
SM
1730 {
1731 printf ("Waiting for Emacs...");
1732 needlf = 2;
1733 }
46cec291 1734 fflush (stdout);
0b0d3e0b 1735 fsync (1);
46cec291 1736
3cf8c6aa 1737 /* Now, wait for an answer and print any messages. */
4b7b77f6 1738 while ((rl = recv (emacs_socket, string, BUFSIZ, 0)) > 0)
3cf8c6aa 1739 {
974b73e8
KL
1740 char *p;
1741 string[rl] = '\0';
1742
1743 p = string + strlen (string) - 1;
1744 while (p > string && *p == '\n')
0b0d3e0b
KL
1745 *p-- = 0;
1746
31fa6595 1747 if (strprefix ("-emacs-pid ", string))
4d553a13 1748 {
6afdd335 1749 /* -emacs-pid PID: The process id of the Emacs process. */
77134727
KL
1750 emacs_pid = strtol (string + strlen ("-emacs-pid"), NULL, 10);
1751 }
974b73e8 1752 else if (strprefix ("-window-system-unsupported ", string))
6afdd335
KL
1753 {
1754 /* -window-system-unsupported: Emacs was compiled without X
1755 support. Try again on the terminal. */
6afdd335
KL
1756 nowait = 0;
1757 tty = 1;
1758 goto retry;
1759 }
974b73e8 1760 else if (strprefix ("-print ", string))
77134727 1761 {
6afdd335 1762 /* -print STRING: Print STRING on the terminal. */
974b73e8 1763 str = unquote_argument (string + strlen ("-print "));
0b0d3e0b 1764 if (needlf)
77134727 1765 printf ("\n");
0b0d3e0b
KL
1766 printf ("%s", str);
1767 needlf = str[0] == '\0' ? needlf : str[strlen (str) - 1] != '\n';
77134727 1768 }
974b73e8 1769 else if (strprefix ("-error ", string))
77134727 1770 {
6afdd335 1771 /* -error DESCRIPTION: Signal an error on the terminal. */
974b73e8 1772 str = unquote_argument (string + strlen ("-error "));
0b0d3e0b
KL
1773 if (needlf)
1774 printf ("\n");
974b73e8 1775 fprintf (stderr, "*ERROR*: %s", str);
0b0d3e0b
KL
1776 needlf = str[0] == '\0' ? needlf : str[strlen (str) - 1] != '\n';
1777 }
c801ad51 1778#ifdef SIGSTOP
382707ec 1779 else if (strprefix ("-suspend ", string))
0b0d3e0b 1780 {
6afdd335 1781 /* -suspend: Suspend this terminal, i.e., stop the process. */
0b0d3e0b 1782 if (needlf)
77134727 1783 printf ("\n");
0b0d3e0b
KL
1784 needlf = 0;
1785 kill (0, SIGSTOP);
4d553a13 1786 }
b2ff54a0 1787#endif
4d553a13
KL
1788 else
1789 {
6afdd335 1790 /* Unknown command. */
0b0d3e0b 1791 if (needlf)
4d553a13 1792 printf ("\n");
974b73e8
KL
1793 printf ("*ERROR*: Unknown message: %s", string);
1794 needlf = string[0] == '\0' ? needlf : string[strlen (string) - 1] != '\n';
4d553a13 1795 }
3cf8c6aa
SM
1796 }
1797
1798 if (needlf)
1799 printf ("\n");
1800 fflush (stdout);
0b0d3e0b 1801 fsync (1);
23a7488d 1802
4b7b77f6 1803 CLOSE_SOCKET (emacs_socket);
65396510 1804 return EXIT_SUCCESS;
46cec291
RS
1805}
1806
1e7823d0 1807#endif /* HAVE_SOCKETS && HAVE_INET_SOCKETS */
aa0b6932 1808
27711600
RM
1809\f
1810#ifndef HAVE_STRERROR
1811char *
1812strerror (errnum)
1813 int errnum;
1814{
1815 extern char *sys_errlist[];
1816 extern int sys_nerr;
1817
1818 if (errnum >= 0 && errnum < sys_nerr)
1819 return sys_errlist[errnum];
1820 return (char *) "Unknown error";
1821}
1822
1823#endif /* ! HAVE_STRERROR */
ab5796a9
MB
1824
1825/* arch-tag: f39bb9c4-73eb-477e-896d-50832e2ca9a7
1826 (do not change this comment) */
65396510
TTN
1827
1828/* emacsclient.c ends here */