Merge pull request #590 from orium/run-as-root-589-504

Now hexchat doesn't abnormally terminate when started as root.
This commit is contained in:
TingPing 2013-05-24 15:01:27 -07:00
commit 270cde42f1
3 changed files with 136 additions and 235 deletions

View File

@ -337,21 +337,10 @@ get_xdir (void)
return xdir; return xdir;
} }
static void int
check_prefs_dir (void) check_config_dir (void)
{ {
char *dir = get_xdir (); return g_access (get_xdir (), F_OK);
char *msg;
if (g_access (dir, F_OK) != 0)
{
if (g_mkdir (dir, 0700) != 0)
{
msg = g_strdup_printf ("Cannot create %s", get_xdir ());
fe_message (msg, FE_MSG_ERROR);
g_free (msg);
}
}
} }
static char * static char *
@ -617,16 +606,14 @@ convert_with_fallback (const char *str, const char *fallback)
} }
void void
load_config (void) load_default_config(void)
{ {
char *cfg, *sp, *buf;
const char *username, *realname; const char *username, *realname;
int res, val, i; char *sp;
#ifdef WIN32 #ifdef WIN32
char out[256]; char out[256];
#endif #endif
check_prefs_dir ();
username = g_get_user_name (); username = g_get_user_name ();
if (!username) if (!username)
username = "root"; username = "root";
@ -800,55 +787,89 @@ load_config (void)
/* private variables */ /* private variables */
prefs.local_ip = 0xffffffff; prefs.local_ip = 0xffffffff;
sp = strchr (prefs.hex_irc_user_name, ' ');
if (sp)
sp[0] = 0; /* spaces in username would break the login */
g_free ((char *)username); g_free ((char *)username);
g_free ((char *)realname); g_free ((char *)realname);
}
if (g_file_get_contents (default_file (), &cfg, NULL, NULL)) int
make_config_dirs (void)
{
char *buf;
if (g_mkdir (get_xdir (), 0700) != 0)
return -1;
buf = g_build_filename (get_xdir (), "addons", NULL);
if (g_mkdir (buf, 0700) != 0)
{ {
i = 0;
do
{
switch (vars[i].type)
{
case TYPE_STR:
cfg_get_str (cfg, vars[i].name, (char *) &prefs + vars[i].offset,
vars[i].len);
break;
case TYPE_BOOL:
case TYPE_INT:
val = cfg_get_int_with_result (cfg, vars[i].name, &res);
if (res)
*((int *) &prefs + vars[i].offset) = val;
break;
}
i++;
}
while (vars[i].name);
g_free (cfg);
} else
{
#ifndef WIN32
#ifndef __EMX__
/* OS/2 uses UID 0 all the time */
if (getuid () == 0)
fe_message (_("* Running IRC as root is stupid! You should\n"
" create a User Account and use that to login.\n"), FE_MSG_WARN|FE_MSG_WAIT);
#endif
#endif /* !WIN32 */
g_mkdir (prefs.hex_dcc_dir, 0700);
g_mkdir (prefs.hex_dcc_completed_dir, 0700);
buf = g_build_filename (get_xdir (), "addons", NULL);
g_mkdir (buf, 0700);
g_free (buf);
buf = g_build_filename (get_xdir (), HEXCHAT_SOUND_DIR, NULL);
g_mkdir (buf, 0700);
g_free (buf); g_free (buf);
return -1;
} }
g_free (buf);
buf = g_build_filename (get_xdir (), HEXCHAT_SOUND_DIR, NULL);
if (g_mkdir (buf, 0700) != 0)
{
g_free (buf);
return -1;
}
g_free (buf);
return 0;
}
int
make_dcc_dirs (void)
{
if (g_mkdir (prefs.hex_dcc_dir, 0700) != 0)
return -1;
if (g_mkdir (prefs.hex_dcc_completed_dir, 0700) != 0)
return -1;
return 0;
}
int
load_config (void)
{
char *cfg, *sp;
int res, val, i;
g_assert(check_config_dir () == 0);
if (!g_file_get_contents (default_file (), &cfg, NULL, NULL))
return -1;
/* If the config is incomplete we have the default values loaded */
load_default_config();
i = 0;
do
{
switch (vars[i].type)
{
case TYPE_STR:
cfg_get_str (cfg, vars[i].name, (char *) &prefs + vars[i].offset,
vars[i].len);
break;
case TYPE_BOOL:
case TYPE_INT:
val = cfg_get_int_with_result (cfg, vars[i].name, &res);
if (res)
*((int *) &prefs + vars[i].offset) = val;
break;
}
i++;
}
while (vars[i].name);
g_free (cfg);
if (prefs.hex_gui_win_height < 138) if (prefs.hex_gui_win_height < 138)
prefs.hex_gui_win_height = 138; prefs.hex_gui_win_height = 138;
if (prefs.hex_gui_win_width < 106) if (prefs.hex_gui_win_width < 106)
@ -857,6 +878,8 @@ load_config (void)
sp = strchr (prefs.hex_irc_user_name, ' '); sp = strchr (prefs.hex_irc_user_name, ' ');
if (sp) if (sp)
sp[0] = 0; /* spaces in username would break the login */ sp[0] = 0; /* spaces in username would break the login */
return 0;
} }
int int
@ -865,7 +888,8 @@ save_config (void)
int fh, i; int fh, i;
char *config, *new_config; char *config, *new_config;
check_prefs_dir (); if (check_config_dir () != 0)
make_config_dirs ();
config = default_file (); config = default_file ();
new_config = g_strconcat (config, ".new", NULL); new_config = g_strconcat (config, ".new", NULL);

View File

@ -34,7 +34,11 @@ int cfg_put_int (int fh, int value, char *var);
int cfg_get_color (char *cfg, char *var, int *r, int *g, int *b); int cfg_get_color (char *cfg, char *var, int *r, int *g, int *b);
int cfg_put_color (int fh, int r, int g, int b, char *var); int cfg_put_color (int fh, int r, int g, int b, char *var);
char *get_xdir (void); char *get_xdir (void);
void load_config (void); int check_config_dir (void);
void load_default_config (void);
int make_config_dirs (void);
int make_dcc_dirs (void);
int load_config (void);
int save_config (void); int save_config (void);
void list_free (GSList ** list); void list_free (GSList ** list);
void list_loadconf (char *file, GSList ** list, char *defaultconf); void list_loadconf (char *file, GSList ** list, char *defaultconf);

View File

@ -1014,16 +1014,37 @@ hexchat_execv (char * const argv[])
#endif #endif
} }
static void
set_locale (void)
{
#ifdef WIN32
const char const *langs[]={
"af", "sq", "am", "ast", "az", "eu", "be", "bg", "ca", "zh_CN", /* 0 .. 9 */
"zh_TW", "cs", "da", "nl", "en_GB", "en", "et", "fi", "fr", "gl", /* 10 .. 19 */
"de", "el", "gu", "hi", "hu", "id", "it", "ja", "kn", "rw", /* 20 .. 29 */
"ko", "lv", "lt", "mk", "ml", "ms", "nb", "no", "pl", "pt", /* 30 .. 39 */
"pt_BR", "pa", "ru", "sr", "sk", "sl", "es", "sv", "th", "uk", /* 40 .. 49 */
"vi", "wa" /* 50 .. */
};
char hexchat_lang[13]; /* LC_ALL= plus 5 chars of hex_gui_lang and trailing \0 */
strcpy (hexchat_lang, "LC_ALL=");
if (0 <= prefs.hex_gui_lang && prefs.hex_gui_lang < sizeof(langs)/sizeof(*langs))
strcat (hexchat_lang, langs[prefs.hex_gui_lang]);
else
strcat (hexchat_lang, "en");
putenv (hexchat_lang);
#endif
}
int int
main (int argc, char *argv[]) main (int argc, char *argv[])
{ {
int i; int i;
int ret; int ret;
#ifdef WIN32
char hexchat_lang[13]; /* LC_ALL= plus 5 chars of hex_gui_lang and trailing \0 */
#endif
srand (time (0)); /* CL: do this only once! */ srand (time (0)); /* CL: do this only once! */
/* We must check for the config dir parameter, otherwise load_config() will behave incorrectly. /* We must check for the config dir parameter, otherwise load_config() will behave incorrectly.
@ -1054,178 +1075,21 @@ main (int argc, char *argv[])
#if ! GLIB_CHECK_VERSION (2, 36, 0) #if ! GLIB_CHECK_VERSION (2, 36, 0)
g_type_init (); g_type_init ();
#endif #endif
load_config ();
#ifdef WIN32 if (check_config_dir () == 0)
/* we MUST do this after load_config () AND before fe_init (thus gtk_init) otherwise it will fail */
strcpy (hexchat_lang, "LC_ALL=");
/* this must be ordered EXACTLY as langsmenu[] */
switch (prefs.hex_gui_lang)
{ {
case 0: if (load_config () != 0)
strcat (hexchat_lang, "af"); load_default_config ();
break; } else
case 1: {
strcat (hexchat_lang, "sq"); /* this is probably the first run */
break; load_default_config ();
case 2: make_config_dirs (); /* FIXME: if this fail display an error (?) */
strcat (hexchat_lang, "am"); make_dcc_dirs ();
break;
case 3:
strcat (hexchat_lang, "ast");
break;
case 4:
strcat (hexchat_lang, "az");
break;
case 5:
strcat (hexchat_lang, "eu");
break;
case 6:
strcat (hexchat_lang, "be");
break;
case 7:
strcat (hexchat_lang, "bg");
break;
case 8:
strcat (hexchat_lang, "ca");
break;
case 9:
strcat (hexchat_lang, "zh_CN");
break;
case 10:
strcat (hexchat_lang, "zh_TW");
break;
case 11:
strcat (hexchat_lang, "cs");
break;
case 12:
strcat (hexchat_lang, "da");
break;
case 13:
strcat (hexchat_lang, "nl");
break;
case 14:
strcat (hexchat_lang, "en_GB");
break;
case 15:
strcat (hexchat_lang, "en");
break;
case 16:
strcat (hexchat_lang, "et");
break;
case 17:
strcat (hexchat_lang, "fi");
break;
case 18:
strcat (hexchat_lang, "fr");
break;
case 19:
strcat (hexchat_lang, "gl");
break;
case 20:
strcat (hexchat_lang, "de");
break;
case 21:
strcat (hexchat_lang, "el");
break;
case 22:
strcat (hexchat_lang, "gu");
break;
case 23:
strcat (hexchat_lang, "hi");
break;
case 24:
strcat (hexchat_lang, "hu");
break;
case 25:
strcat (hexchat_lang, "id");
break;
case 26:
strcat (hexchat_lang, "it");
break;
case 27:
strcat (hexchat_lang, "ja");
break;
case 28:
strcat (hexchat_lang, "kn");
break;
case 29:
strcat (hexchat_lang, "rw");
break;
case 30:
strcat (hexchat_lang, "ko");
break;
case 31:
strcat (hexchat_lang, "lv");
break;
case 32:
strcat (hexchat_lang, "lt");
break;
case 33:
strcat (hexchat_lang, "mk");
break;
case 34:
strcat (hexchat_lang, "ml");
break;
case 35:
strcat (hexchat_lang, "ms");
break;
case 36:
strcat (hexchat_lang, "nb");
break;
case 37:
strcat (hexchat_lang, "no");
break;
case 38:
strcat (hexchat_lang, "pl");
break;
case 39:
strcat (hexchat_lang, "pt");
break;
case 40:
strcat (hexchat_lang, "pt_BR");
break;
case 41:
strcat (hexchat_lang, "pa");
break;
case 42:
strcat (hexchat_lang, "ru");
break;
case 43:
strcat (hexchat_lang, "sr");
break;
case 44:
strcat (hexchat_lang, "sk");
break;
case 45:
strcat (hexchat_lang, "sl");
break;
case 46:
strcat (hexchat_lang, "es");
break;
case 47:
strcat (hexchat_lang, "sv");
break;
case 48:
strcat (hexchat_lang, "th");
break;
case 49:
strcat (hexchat_lang, "uk");
break;
case 50:
strcat (hexchat_lang, "vi");
break;
case 51:
strcat (hexchat_lang, "wa");
break;
default:
strcat (hexchat_lang, "en");
break;
} }
putenv (hexchat_lang); /* we MUST do this after load_config () AND before fe_init (thus gtk_init) otherwise it will fail */
#endif set_locale ();
#ifdef SOCKS #ifdef SOCKS
SOCKSinit (argv[0]); SOCKSinit (argv[0]);
@ -1245,6 +1109,15 @@ main (int argc, char *argv[])
fe_init (); fe_init ();
#ifndef WIN32
#ifndef __EMX__
/* OS/2 uses UID 0 all the time */
if (getuid () == 0)
fe_message (_("* Running IRC as root is stupid! You should\n"
" create a User Account and use that to login.\n"), FE_MSG_WARN|FE_MSG_WAIT);
#endif
#endif /* !WIN32 */
xchat_init (); xchat_init ();
fe_main (); fe_main ();