lib/eggdrop/users.c File Reference

#include <eggdrop/eggdrop.h>

Go to the source code of this file.

Data Structures

struct  walker_info_t
struct  cmd_match_data_t

Defines

#define BAD_HANDLE_CHARS   " *?@:"

Functions

static user_treal_user_new (const char *handle, int uid)
static int user_get_uid ()
static int cache_check_add (const void *key, void *dataptr, void *client_data)
static int cache_check_del (const void *key, void *dataptr, void *client_data)
static int cache_rand_cleanup (const char *event)
static int cache_user_del (user_t *u, const char *ircmask)
static void append_setting (user_t *u, const char *chan, const char *flag_str, xml_node_t *extended)
static int userlist_delete_walker (const void *key, void *dataptr, void *client_data)
int user_init (void)
int user_shutdown (void)
void user_walk (hash_table_node_func callback, void *data)
int user_load (const char *fname)
static int save_walker (const void *key, void *dataptr, void *param)
static int unlink_walker (const void *key, void *dataptr, void *param)
int user_save (const char *fname)
const char * user_invalid_handle (const char *handle)
user_tuser_new (const char *handle)
static int user_really_delete (void *client_data)
int user_delete (user_t *u)
user_tuser_lookup_by_handle (const char *handle)
user_tuser_lookup_authed (const char *handle, const char *pass)
user_tuser_lookup_by_uid (int uid)
user_tuser_lookup_by_irchost_nocache (const char *irchost)
user_tuser_lookup_by_irchost (const char *irchost)
int user_add_ircmask (user_t *u, const char *ircmask)
int user_del_ircmask (user_t *u, const char *ircmask)
static int get_flags (user_t *u, const char *chan, flags_t **flags)
int user_get_flags (user_t *u, const char *chan, flags_t *flags)
static int check_flag_change (user_t *u, const char *chan, flags_t *oldflags, flags_t *newflags)
int user_set_flags (user_t *u, const char *chan, flags_t *flags)
int user_set_flags_str (user_t *u, const char *chan, const char *flags)
static xml_node_tfind_setting (user_t *u, const char *chan, const char *name, int create)
int user_get_setting (user_t *u, const char *chan, const char *setting, char **valueptr)
int user_set_setting (user_t *u, const char *chan, const char *setting, const char *value)
int user_has_pass (user_t *u)
int user_check_pass (user_t *u, const char *pass)
int user_set_pass (user_t *u, const char *pass)
int user_count ()
int user_rand_pass (char *buf, int bufsize)
int user_check_flags (user_t *u, const char *chan, flags_t *flags)
int user_check_flags_str (user_t *u, const char *chan, const char *flags)
int user_check_partial_flags (user_t *u, const char *chan, flags_t *flags)
int user_check_partial_flags_str (user_t *u, const char *chan, const char *flags)
int user_change_handle (user_t *u, const char *newhandle)
static int ircmask_matches_user (user_t *u, const char *wild)
static int attr_matches_user (user_t *u, cmd_match_data_t *mdata)
static int callback_match_attr (const char *key, char **data, cmd_match_data_t *mdata)
static int callback_match_ircmask (const char *key, char **data, cmd_match_data_t *mdata)
int partyline_cmd_match_ircmask (void *p, const char *mask, long start, long limit)
int partyline_cmd_match_attr (void *p, const char *attr, const char *chan, long start, long limit)

Variables

static const char rcsid [] = "$Id: users.c,v 1.56 2007-05-10 00:25:07 sven Exp $"
static int g_uid = 1
static int uid_wraparound = 0
static int nusers = 0
static hash_table_tirchost_cache_ht = NULL
static hash_table_thandle_ht = NULL
static hash_table_tuid_ht = NULL
static ircmask_list_t ircmask_list = {NULL}
static bind_table_tBT_uflags = NULL
static bind_table_tBT_uset = NULL
static bind_table_tBT_udelete = NULL


Define Documentation

#define BAD_HANDLE_CHARS   " *?@:"

Definition at line 46 of file users.c.

Referenced by user_invalid_handle().


Function Documentation

static void append_setting ( user_t u,
const char *  chan,
const char *  flag_str,
xml_node_t extended 
) [static]

Definition at line 656 of file users.c.

References flags_t::builtin, user_setting_t::chan, user_setting_t::extended, flag_from_str(), user::flags, user_setting_t::flags, xml_node::name, user::nsettings, user::settings, USER_BOT, xml_node_new(), and xml_node_unlink().

Referenced by find_setting(), user_load(), user_set_flags(), and user_set_flags_str().

00657 {
00658   user_setting_t *setting;
00659   u->settings = realloc(u->settings, sizeof(*u->settings) * (u->nsettings+1));
00660   setting = u->settings + u->nsettings;
00661   u->nsettings++;
00662   memset(setting, 0, sizeof(*setting));
00663   if (chan) setting->chan = strdup(chan);
00664   if (flag_str) flag_from_str(&setting->flags, flag_str);
00665   if (!chan && setting->flags.builtin & 2) u->flags |= USER_BOT;
00666   if (extended) {
00667     xml_node_unlink(extended);
00668     setting->extended = extended;
00669   }
00670   else {
00671     setting->extended = xml_node_new();
00672     setting->extended->name = strdup("extended");
00673   }
00674 }

static int attr_matches_user ( user_t u,
cmd_match_data_t mdata 
) [static]

Definition at line 853 of file users.c.

References flags_t::builtin, cmd_match_data_t::channel, cmd_match_data_t::data, flag_match_partial(), flag_match_subset(), cmd_match_data_t::musthave, cmd_match_data_t::mustnothave, NULL, flags_t::udef, and user_get_flags().

Referenced by callback_match_attr().

00854 {
00855   int matched = 0, haschanflags = 0;
00856   flags_t globflags, chanflags;
00857 
00858   chanflags.builtin = chanflags.udef = 0;
00859 
00860   if (user_get_flags(u, NULL, &globflags))
00861     return 0;
00862 
00863   if (mdata->channel) {
00864     haschanflags = !user_get_flags(u, mdata->channel, &chanflags);
00865     if (!haschanflags)
00866       return 0;
00867   }
00868 
00869   if ((mdata->musthave[0].builtin | mdata->musthave[0].udef) && /* Non empty needed flags */
00870     flag_match_subset(&mdata->musthave[0], &globflags) && /* ..AND they match */
00871     (!(mdata->mustnothave[0].builtin | mdata->mustnothave[0].udef) || /* AND (empty forbiden flags */
00872     !flag_match_partial(&globflags, &mdata->mustnothave[0])) /* OR forbiden flags don't match) */
00873     )
00874     matched = 1;
00875 
00876   if (mdata->data) { /* mdata->data points to '|' or '&' if it existed,
00877         which means channel flags are needed too */
00878     int tmpyes = mdata->musthave[1].builtin | mdata->musthave[1].udef;
00879     int tmpnot = mdata->mustnothave[1].builtin | mdata->mustnothave[1].udef;
00880     if (*mdata->data == '|') {
00881 
00882       return (matched || /* Either we already matched OR .. */
00883         ((tmpyes && flag_match_subset(&mdata->musthave[1], &chanflags)) && /*Non-empty needed
00884                         flags match, AND */
00885         (!tmpnot || !flag_match_partial(&chanflags, &mdata->mustnothave[1]))) /* There are no
00886                           forbidden flags OR
00887                           they don't match */
00888         );
00889     }
00890     else if (*mdata->data == '&')
00891       return (matched && /* Global flags match AND .. */
00892         ((tmpyes && flag_match_subset(&mdata->musthave[1], &chanflags)) &&
00893         (!tmpnot || !flag_match_partial(&chanflags, &mdata->mustnothave[1])))
00894         );
00895     else
00896       return 0;
00897   }
00898 
00899   return matched;
00900 }

static int cache_check_add ( const void *  key,
void *  dataptr,
void *  client_data 
) [static]

Definition at line 443 of file users.c.

References walker_info_t::ircmask, user::ircmasks, user::nircmasks, walker_info_t::u, and wild_match().

Referenced by user_add_ircmask().

00444 {
00445   const char *irchost = key;
00446   user_t *u = *(user_t **)dataptr;
00447   walker_info_t *info = client_data;
00448   int i, strength, max_strength;
00449 
00450   /* Get the strength of the current match. */
00451   max_strength = 0;
00452   if (u) {
00453     for (i = 0; i < u->nircmasks; i++) {
00454       strength = wild_match(u->ircmasks[i], irchost);
00455       if (strength > max_strength) max_strength = strength;
00456     }
00457   }
00458 
00459   /* And now the strength of the the new mask. */
00460   strength = wild_match(info->ircmask, irchost);
00461   if (strength > max_strength) {
00462     /* Ok, replace it. */
00463     *(user_t **)dataptr = info->u;
00464   }
00465   return(0);
00466 }

static int cache_check_del ( const void *  key,
void *  dataptr,
void *  client_data 
) [static]

Definition at line 468 of file users.c.

References walker_info_t::entries, walker_info_t::ircmask, walker_info_t::maxentries, walker_info_t::nentries, walker_info_t::rand_delete, walker_info_t::u, and wild_match().

Referenced by cache_rand_cleanup(), and cache_user_del().

00469 {
00470   const char *irchost = key;
00471   user_t *u = *(user_t **)dataptr;
00472   walker_info_t *info = client_data;
00473 
00474   if ((info->rand_delete && (rand() & 1)) || (!info->rand_delete && u == info->u && wild_match(info->ircmask, irchost))) {
00475     if (info->nentries >= info->maxentries) {
00476       info->maxentries = 2*info->maxentries+1;
00477       info->entries = realloc(info->entries, sizeof(*info->entries) * (info->maxentries+1));
00478     }
00479     info->entries[info->nentries] = irchost;
00480     info->nentries++;
00481   }
00482   return(0);
00483 }

static int cache_rand_cleanup ( const char *  event  )  [static]

Definition at line 508 of file users.c.

References cache_check_del(), walker_info_t::entries, hash_table_remove(), hash_table_walk(), walker_info_t::ircmask, LOG_MISC, walker_info_t::maxentries, walker_info_t::nentries, NULL, putlog(), walker_info_t::rand_delete, and walker_info_t::u.

Referenced by user_init().

00509 {
00510   walker_info_t info;
00511   int i;
00512 
00513   /* Check irchost_cache_ht for changes in the users. */
00514   info.u = NULL;
00515   info.ircmask = NULL;
00516   info.entries = NULL;
00517   info.nentries = 0;
00518   info.maxentries = 0;
00519   info.rand_delete = 1;
00520   hash_table_walk(irchost_cache_ht, cache_check_del, &info);
00521   putlog(LOG_MISC, "*", "user_rand_cleanup: deleting %d entries from cache", info.nentries);
00522   for (i = 0; i < info.nentries; i++) {
00523     hash_table_remove(irchost_cache_ht, info.entries[i], NULL);
00524   }
00525   if (info.entries) free(info.entries);
00526   return(0);
00527 }

static int cache_user_del ( user_t u,
const char *  ircmask 
) [static]

Definition at line 485 of file users.c.

References cache_check_del(), walker_info_t::entries, hash_table_remove(), hash_table_walk(), walker_info_t::ircmask, ircmask_list_del(), walker_info_t::maxentries, walker_info_t::nentries, NULL, walker_info_t::rand_delete, and walker_info_t::u.

Referenced by user_del_ircmask(), and user_delete().

00486 {
00487   walker_info_t info;
00488   int i;
00489 
00490   /* Check irchost_cache_ht for changes in the users. */
00491   info.u = u;
00492   info.ircmask = ircmask;
00493   info.entries = NULL;
00494   info.nentries = 0;
00495   info.maxentries = 0;
00496   info.rand_delete = 0;
00497   hash_table_walk(irchost_cache_ht, cache_check_del, &info);
00498   for (i = 0; i < info.nentries; i++) {
00499     hash_table_remove(irchost_cache_ht, info.entries[i], NULL);
00500   }
00501   if (info.entries) free(info.entries);
00502 
00503   /* And remove it from the ircmask_list. */
00504   ircmask_list_del(&ircmask_list, ircmask, u);
00505   return(0);
00506 }

static int callback_match_attr ( const char *  key,
char **  data,
cmd_match_data_t mdata 
) [static]

Definition at line 911 of file users.c.

References _, attr_matches_user(), cmd_match_data_t::limit, partymember_printf(), cmd_match_data_t::pmember, cmd_match_data_t::start, and user_lookup_by_handle().

Referenced by partyline_cmd_match_attr().

00912 {
00913   user_t *u = user_lookup_by_handle(key);
00914 
00915   if (!u)
00916     return 0;
00917 
00918   if (mdata->start && attr_matches_user(u, mdata)) {
00919     mdata->start--;
00920     return 0;
00921   }
00922 
00923   if (mdata->limit && attr_matches_user(u, mdata)) {
00924     mdata->limit--;
00925     partymember_printf(mdata->pmember, _("  %s"), key);
00926   }
00927 
00928   return 0;
00929 }

static int callback_match_ircmask ( const char *  key,
char **  data,
cmd_match_data_t mdata 
) [static]

Definition at line 932 of file users.c.

References _, cmd_match_data_t::data, ircmask_matches_user(), cmd_match_data_t::limit, partymember_printf(), cmd_match_data_t::pmember, cmd_match_data_t::start, user_lookup_by_handle(), and wild_match().

Referenced by partyline_cmd_match_ircmask().

00933 {
00934   user_t *u = user_lookup_by_handle(key);
00935 
00936   if (!u)
00937     return 0;
00938 
00939   if (mdata->start && (wild_match(mdata->data, key) || ircmask_matches_user(u, mdata->data))) {
00940     mdata->start--;
00941     return 0;
00942   }
00943 
00944   if (mdata->limit && (wild_match(mdata->data, key) || ircmask_matches_user(u, mdata->data))) {
00945     mdata->limit--;
00946     partymember_printf(mdata->pmember, _("  %s"), key);
00947   }
00948 
00949   return 0;
00950 }

static int check_flag_change ( user_t u,
const char *  chan,
flags_t oldflags,
flags_t newflags 
) [static]

Definition at line 594 of file users.c.

References bind_check(), BIND_RET_BREAK, flags_t::builtin, egg_msprintf(), flag_to_str(), user::flags, user::handle, NULL, USER_BOT, USER_LINKED_BOT, and USER_LINKING_BOT.

Referenced by user_set_flags(), and user_set_flags_str().

00595 {
00596   char oldstr[64], newstr[64], *change;
00597   int r;
00598 
00599   if (u->flags & (USER_LINKING_BOT | USER_LINKED_BOT) && !chan && (oldflags->builtin & 2) != (newflags->builtin & 2)) return -1;
00600   flag_to_str(oldflags, oldstr);
00601   flag_to_str(newflags, newstr);
00602   change = egg_msprintf(NULL, 0, NULL, "%s %s %s", chan ? chan : "", oldstr, newstr);
00603   r = bind_check(BT_uflags, NULL, change, u->handle, chan, oldstr, newstr);
00604   free(change);
00605 
00606   /* Does a callback want to cancel this flag change? */
00607   if (r & BIND_RET_BREAK) return(-1);
00608   if (!chan) {
00609     if (newflags->builtin & 2) u->flags |= USER_BOT;
00610     else u->flags &= ~USER_BOT;
00611   }
00612   return(0);
00613 }

static xml_node_t* find_setting ( user_t u,
const char *  chan,
const char *  name,
int  create 
) [static]

Definition at line 676 of file users.c.

References append_setting(), user_setting_t::chan, user_setting_t::extended, user::nsettings, NULL, user::settings, and xml_node_lookup().

Referenced by user_get_setting(), and user_set_setting().

00677 {
00678   user_setting_t *setting;
00679   int i = 0;
00680 
00681   if (chan) for (i = 1; i < u->nsettings; i++) {
00682     if (!strcasecmp(chan, u->settings[i].chan)) break;
00683   }
00684   if (i >= u->nsettings) {
00685     if (!create) return(NULL);
00686     append_setting(u, chan, NULL, NULL);
00687   }
00688   setting = u->settings+i;
00689   return xml_node_lookup(setting->extended, create, name, 0, NULL);
00690 }

static int get_flags ( user_t u,
const char *  chan,
flags_t **  flags 
) [static]

Definition at line 568 of file users.c.

References user_setting_t::chan, user_setting_t::flags, user::nsettings, and user::settings.

Referenced by user_get_flags(), user_set_flags(), and user_set_flags_str().

00569 {
00570   int i;
00571 
00572   if (!chan) i = 0;
00573   else {
00574     for (i = 1; i < u->nsettings; i++) {
00575       if (!strcasecmp(chan, u->settings[i].chan)) break;
00576     }
00577     if (i == u->nsettings) return(-1);
00578   }
00579   *flags = &u->settings[i].flags;
00580   return(0);
00581 }

static int ircmask_matches_user ( user_t u,
const char *  wild 
) [static]

Definition at line 842 of file users.c.

References user::ircmasks, user::nircmasks, and wild_match().

Referenced by callback_match_ircmask().

00843 {
00844   int i;
00845 
00846   for (i = 0; i < u->nircmasks; i++)
00847     if (wild_match(wild, u->ircmasks[i]))
00848       return 1;
00849   return 0;
00850 }

int partyline_cmd_match_attr ( void *  p,
const char *  attr,
const char *  chan,
long  start,
long  limit 
)

Definition at line 969 of file users.c.

References flags_t::builtin, callback_match_attr(), cmd_match_data_t::channel, cmd_match_data_t::data, flag_merge_str(), hash_table_walk(), cmd_match_data_t::limit, cmd_match_data_t::musthave, cmd_match_data_t::mustnothave, NULL, cmd_match_data_t::pmember, cmd_match_data_t::start, and flags_t::udef.

Referenced by party_matchattr().

00970 {
00971   cmd_match_data_t mdata;
00972   int plsmns = 1, globchan = 0;
00973   char flagshack[] = "+ "; /* Hack to allow us to use flag_merge_str */
00974 
00975   mdata.start = start;
00976   mdata.limit = limit;
00977 /* FIXME - Once we sort #includes, 'p' should be partymember_t in function declaration */
00978   mdata.pmember = (partymember_t *)p;
00979   mdata.data = NULL;
00980   mdata.channel = chan;
00981   mdata.musthave[0].builtin = mdata.musthave[0].udef = 0;
00982   mdata.mustnothave[0].builtin = mdata.mustnothave[0].udef = 0;
00983   mdata.musthave[1].builtin = mdata.musthave[1].udef = 0;
00984   mdata.mustnothave[1].builtin = mdata.mustnothave[1].udef = 0;
00985 
00986   while (*attr) {
00987     switch (*attr) {
00988       case '+':
00989         plsmns = 1;
00990         break;
00991       case '-':
00992         plsmns = 0;
00993         break;
00994       case '&':
00995       case '|':
00996         if (globchan == 0) { /* Consider only the first & or | */
00997           globchan++;
00998           mdata.data = attr;
00999         }
01000         break;
01001       default:
01002         flagshack[1] = *attr;
01003         flag_merge_str(plsmns ? &mdata.musthave[globchan] :
01004               &mdata.mustnothave[globchan], flagshack);
01005         break;
01006     }
01007     attr++;
01008   }
01009 
01010   hash_table_walk(handle_ht, (hash_table_node_func)callback_match_attr, &mdata);
01011 
01012   return 0;
01013 }

int partyline_cmd_match_ircmask ( void *  p,
const char *  mask,
long  start,
long  limit 
)

Definition at line 953 of file users.c.

References callback_match_ircmask(), cmd_match_data_t::data, hash_table_walk(), cmd_match_data_t::limit, cmd_match_data_t::pmember, and cmd_match_data_t::start.

Referenced by party_matchwild().

00954 {
00955   cmd_match_data_t mdata;
00956 
00957   mdata.start = start;
00958   mdata.limit = limit;
00959 /* FIXME - Once we sort #includes, 'p' should be partymember_t in function declaration */
00960   mdata.pmember = (partymember_t *)p;
00961   mdata.data = mask;
00962 
00963   hash_table_walk(handle_ht, (hash_table_node_func)callback_match_ircmask, &mdata);
00964 
00965   return 0;
00966 }

static user_t * real_user_new ( const char *  handle,
int  uid 
) [static]

Definition at line 311 of file users.c.

References user::handle, hash_table_insert(), NULL, nusers, user::uid, user_get_uid(), and user_invalid_handle().

Referenced by user_load(), and user_new().

00312 {
00313   user_t *u;
00314 
00315   /* Make sure the handle is valid. */
00316   if (user_invalid_handle(handle)) return(NULL);
00317 
00318   u = calloc(1, sizeof(*u));
00319   u->handle = strdup(handle);
00320   if (!uid) uid = user_get_uid();
00321   u->uid = uid;
00322 
00323   hash_table_insert(handle_ht, u->handle, u);
00324   hash_table_insert(uid_ht, (void *)u->uid, u);
00325   nusers++;
00326   return(u);
00327 }

static int save_walker ( const void *  key,
void *  dataptr,
void *  param 
) [static]

Definition at line 222 of file users.c.

References user_setting_t::chan, user_setting_t::extended, flag_to_str(), user_setting_t::flags, user::handle, user::ircmasks, xml_node::name, user::nircmasks, user::nsettings, user::settings, user::uid, xml_node_append(), xml_node_new(), xml_node_set_int(), and xml_node_set_str().

Referenced by user_save().

00223 {
00224   xml_node_t *root = param;
00225   user_t *u = *(user_t **)dataptr;
00226   user_setting_t *setting;
00227   xml_node_t *user_node, *setting_node;
00228   int i;
00229   char flag_str[128];
00230 
00231   user_node = xml_node_new();
00232   user_node->name = strdup("user");
00233   xml_node_set_str(u->handle, user_node, "handle", 0, 0);
00234   xml_node_set_int(u->uid, user_node, "uid", 0, 0);
00235   for (i = 0; i < u->nircmasks; i++) xml_node_set_str(u->ircmasks[i], user_node, "ircmask", i, 0);
00236   for (i = 0; i < u->nsettings; i++) {
00237     setting = u->settings+i;
00238     setting_node = xml_node_new();
00239     setting_node->name = strdup("setting");
00240     if (setting->chan) xml_node_set_str(setting->chan, setting_node, "chan", 0, 0);
00241     flag_to_str(&u->settings[i].flags, flag_str);
00242     xml_node_set_str(flag_str, setting_node, "flags", 0, 0);
00243     xml_node_append(setting_node, u->settings[i].extended);
00244     xml_node_append(user_node, setting_node);
00245   }
00246   xml_node_append(root, user_node);
00247   return(0);
00248 }

static int unlink_walker ( const void *  key,
void *  dataptr,
void *  param 
) [static]

Definition at line 250 of file users.c.

References user_setting_t::extended, user::nsettings, user::settings, and xml_node_unlink().

Referenced by user_save().

00251 {
00252   user_t *u = *(user_t **)dataptr;
00253   int i;
00254 
00255   for (i = 0; i < u->nsettings; i++) {
00256     xml_node_unlink(u->settings[i].extended);
00257   }
00258   return(0);
00259 }

int user_add_ircmask ( user_t u,
const char *  ircmask 
)

Definition at line 529 of file users.c.

References cache_check_add(), hash_table_walk(), walker_info_t::ircmask, ircmask_list_add(), user::ircmasks, user::nircmasks, and walker_info_t::u.

Referenced by AddMask(), and party_plus_host().

00530 {
00531   walker_info_t info;
00532 
00533   /* Add the ircmask to the user entry. */
00534   u->ircmasks = (char **)realloc(u->ircmasks, sizeof(char *) * (u->nircmasks+1));
00535   u->ircmasks[u->nircmasks] = strdup(ircmask);
00536   u->nircmasks++;
00537 
00538   /* Put it in the big list. */
00539   ircmask_list_add(&ircmask_list, ircmask, u);
00540 
00541   /* Check irchost_cache_ht for changes in the users. */
00542   info.u = u;
00543   info.ircmask = ircmask;
00544   hash_table_walk(irchost_cache_ht, cache_check_add, &info);
00545   return(0);
00546 }

int user_change_handle ( user_t u,
const char *  newhandle 
)

Definition at line 824 of file users.c.

References user::handle, hash_table_insert(), hash_table_remove(), NULL, partymember_lookup(), partymember_set_nick(), and user_invalid_handle().

Referenced by party_chhandle().

00825 {
00826   char *old = u->handle;
00827   partymember_t *p = NULL;
00828 
00829   if (user_invalid_handle(newhandle)) return 1;
00830   hash_table_remove(handle_ht, u->handle, NULL);
00831   u->handle = strdup(newhandle);
00832   hash_table_insert(handle_ht, u->handle, u);
00833 
00834   while ((p = partymember_lookup(old, NULL, -1))) {
00835     partymember_set_nick(p, u->handle);
00836   }
00837 
00838   free(u->handle);
00839   return(0);
00840 }

int user_check_flags ( user_t u,
const char *  chan,
flags_t flags 
)

Definition at line 792 of file users.c.

References flag_match_subset(), and user_get_flags().

Referenced by user_check_flags_str().

00793 {
00794   flags_t f;
00795 
00796   user_get_flags(u, chan, &f);
00797   return flag_match_subset(flags, &f);
00798 }

int user_check_flags_str ( user_t u,
const char *  chan,
const char *  flags 
)

Definition at line 800 of file users.c.

References flag_from_str(), and user_check_flags().

Referenced by party_chanmembermode().

00801 {
00802   flags_t f;
00803 
00804   flag_from_str(&f, flags);
00805   return user_check_flags(u, chan, &f);
00806 }

int user_check_partial_flags ( user_t u,
const char *  chan,
flags_t flags 
)

Definition at line 808 of file users.c.

References flag_match_partial(), and user_get_flags().

Referenced by user_check_partial_flags_str().

00809 {
00810   flags_t f;
00811 
00812   user_get_flags(u, chan, &f);
00813   return flag_match_partial(flags, &f);
00814 }

int user_check_partial_flags_str ( user_t u,
const char *  chan,
const char *  flags 
)

Definition at line 816 of file users.c.

References flag_from_str(), and user_check_partial_flags().

Referenced by party_chanmembermode().

00817 {
00818   flags_t f;
00819 
00820   flag_from_str(&f, flags);
00821   return user_check_partial_flags(u, chan, &f);
00822 }

int user_check_pass ( user_t u,
const char *  pass 
)

Definition at line 725 of file users.c.

References MD5_Final(), MD5_Hex(), MD5_Init(), MD5_Update(), NULL, and user_get_setting().

Referenced by CheckPass(), and user_lookup_authed().

00726 {
00727   char *hash, *salt, testhex[33];
00728   unsigned char test[16];
00729   MD5_CTX ctx;
00730 
00731   user_get_setting(u, NULL, "pass", &hash);
00732   user_get_setting(u, NULL, "salt", &salt);
00733   if (!hash || !salt || !strcmp(hash, "none")) return(0);
00734 
00735   MD5_Init(&ctx);
00736   MD5_Update(&ctx, salt, strlen(salt));
00737   MD5_Update(&ctx, pass, strlen(pass));
00738   MD5_Final(test, &ctx);
00739   MD5_Hex(test, testhex);
00740   return !strcasecmp(testhex, hash);
00741 }

int user_count (  ) 

Definition at line 769 of file users.c.

References nusers.

Referenced by create_userfile().

00770 {
00771   return(nusers);
00772 }

int user_del_ircmask ( user_t u,
const char *  ircmask 
)

Definition at line 548 of file users.c.

References cache_user_del(), user::ircmasks, and user::nircmasks.

Referenced by DelMask(), and party_minus_host().

00549 {
00550   int i;
00551 
00552   /* Find the ircmask in the user entry. */
00553   for (i = 0; i < u->nircmasks; i++) {
00554     if (!strcasecmp(u->ircmasks[i], ircmask)) break;
00555   }
00556   if (i == u->nircmasks) return(-1);
00557 
00558   /* Get rid of it. */
00559   memmove(u->ircmasks+i, u->ircmasks+i+1, sizeof(char *) * (u->nircmasks - i - 1));
00560   u->nircmasks--;
00561 
00562   /* Delete matching entries of this user in the host cache. */
00563   cache_user_del(u, ircmask);
00564 
00565   return(0);
00566 }

int user_delete ( user_t u  ) 

int user_get_flags ( user_t u,
const char *  chan,
flags_t flags 
)

Definition at line 583 of file users.c.

References flags_t::builtin, get_flags(), and flags_t::udef.

Referenced by attr_matches_user(), GetFlags(), MatchFlags(), MatchFlagsOr(), party_chattr(), party_whois(), script_getflags(), script_matchflags(), user_check_flags(), and user_check_partial_flags().

00584 {
00585   flags_t *uflags;
00586 
00587   if (get_flags(u, chan, &uflags)) return(-1);
00588 
00589   flags->builtin = uflags->builtin;
00590   flags->udef = uflags->udef;
00591   return(0);
00592 }

int user_get_setting ( user_t u,
const char *  chan,
const char *  setting,
char **  valueptr 
)

static int user_get_uid (  )  [static]

Definition at line 280 of file users.c.

References g_uid, hash_table_find(), and uid_wraparound.

Referenced by real_user_new(), and user_new().

00281 {
00282   user_t *u;
00283   int uid;
00284 
00285   if (g_uid <= 0) {
00286     g_uid = 1;
00287     uid_wraparound++;
00288   }
00289 
00290   /* If we've wrapped around on uids, we need to search for a free one. */
00291   if (uid_wraparound) {
00292     while (!hash_table_find(uid_ht, (void *)g_uid, &u)) g_uid++;
00293   }
00294 
00295   uid = g_uid;
00296   g_uid++;
00297   return(uid);
00298 }

int user_has_pass ( user_t u  ) 

Definition at line 715 of file users.c.

References NULL, and user_get_setting().

Referenced by HasPass().

00716 {
00717   char *hash, *salt;
00718 
00719   user_get_setting(u, NULL, "pass", &hash);
00720   user_get_setting(u, NULL, "salt", &salt);
00721   if (hash && salt && strcmp(hash, "none")) return(1);
00722   return(0);
00723 }

int user_init ( void   ) 

const char* user_invalid_handle ( const char *  handle  ) 

Definition at line 300 of file users.c.

References _, BAD_HANDLE_CHARS, NULL, and user_lookup_by_handle().

Referenced by party_chhandle(), party_plus_user(), real_user_new(), and user_change_handle().

00301 {
00302   if (user_lookup_by_handle(handle)) return _("Handle already exists!");
00303   for (; *handle; ++handle) {
00304     if (*handle < 32 || strchr(BAD_HANDLE_CHARS, *handle)) {
00305       return _("Handle contains invalid characters!");
00306     }
00307   }
00308   return NULL;
00309 }

int user_load ( const char *  fname  ) 

Definition at line 170 of file users.c.

References _, append_setting(), g_uid, ircmask_list_add(), user::ircmasks, LOG_MISC, xml_node::next_sibling, user::nircmasks, NULL, nusers, putlog(), real_user_new(), uid_wraparound, xml_doc_delete(), xml_last_error(), xml_node_get_vars(), xml_node_lookup(), xml_node_str(), and xml_parse_file().

Referenced by core_init().

00171 {
00172   int uid;
00173   xml_node_t *root, *user_node, *ircmask_node, *setting_node, *extended_node;
00174   char *handle, *ircmask, *chan, *flag_str;
00175   user_t *u;
00176 
00177   if (!(root = xml_parse_file(fname))) {
00178     putlog(LOG_MISC, "*", _("Failed to load userfile '%s': %s"), fname, xml_last_error());
00179     return -1;
00180   }
00181 
00182   xml_node_get_vars(root, "ii", "next_uid", &uid, "uid_wraparound", &uid_wraparound);
00183   g_uid = uid;
00184 
00185   user_node = xml_node_lookup(root, 0, "user", 0, 0);
00186   for (; user_node; user_node = user_node->next_sibling) {
00187     /* The only required user fields are 'handle' and 'uid'. */
00188     xml_node_get_vars(user_node, "sinn", "handle", &handle, "uid", &uid, "ircmask", &ircmask_node, "setting", &setting_node);
00189 
00190     if (!handle || !uid) continue;
00191     u = real_user_new(handle, uid);
00192 
00193     /* User already exists? */
00194     if (!u) continue;
00195 
00196     /* Irc masks. */
00197     for (; ircmask_node; ircmask_node = ircmask_node->next_sibling) {
00198       ircmask = xml_node_str(ircmask_node, NULL);
00199       if (!ircmask) continue;
00200       u->ircmasks = realloc(u->ircmasks, sizeof(char *) * (u->nircmasks+1));
00201       u->ircmasks[u->nircmasks] = strdup(ircmask);
00202       u->nircmasks++;
00203       ircmask_list_add(&ircmask_list, ircmask, u);
00204     }
00205 
00206     /* Settings. */
00207     /* They have to have at least 1 setting, the global one. */
00208     if (!setting_node) append_setting(u, NULL, NULL, NULL);
00209     for (; setting_node; setting_node = setting_node->next_sibling) {
00210       xml_node_get_vars(setting_node, "ssn", "chan", &chan, "flags", &flag_str, "extended", &extended_node);
00211       append_setting(u, chan, flag_str, extended_node);
00212     }
00213   }
00214   xml_doc_delete(root);
00215 
00216   if (nusers == 1) putlog(LOG_MISC, "*", _("Loaded 1 user"));
00217   else putlog(LOG_MISC, "*", _("Loaded %d users"), nusers);
00218 
00219   return(0);
00220 }

user_t* user_lookup_authed ( const char *  handle,
const char *  pass 
)

Definition at line 400 of file users.c.

References NULL, user_check_pass(), and user_lookup_by_handle().

Referenced by dcc_on_read(), irc_on_read(), and telnet_on_read().

00401 {
00402   user_t *u = user_lookup_by_handle(handle);
00403   if (!u) return(NULL);
00404   if (user_check_pass(u, pass)) return(u);
00405   return(NULL);
00406 }

user_t* user_lookup_by_handle ( const char *  handle  ) 

user_t* user_lookup_by_irchost ( const char *  irchost  ) 

Definition at line 428 of file users.c.

References hash_table_find(), hash_table_insert(), and ircmask_list_find().

Referenced by party_channels(), process_results(), and server_parse_input().

00429 {
00430   user_t *u;
00431 
00432   /* Check the irchost cache. */
00433   if (!hash_table_find(irchost_cache_ht, irchost, &u)) return(u);
00434 
00435   /* Look for a match in the ircmask list. */
00436   ircmask_list_find(&ircmask_list, irchost, &u);
00437 
00438   /* Cache it, even if it's null (to prevent future lookups). */
00439   hash_table_insert(irchost_cache_ht, strdup(irchost), u);
00440   return(u);
00441 }

user_t* user_lookup_by_irchost_nocache ( const char *  irchost  ) 

Definition at line 416 of file users.c.

References hash_table_find(), and ircmask_list_find().

Referenced by goterror(), and script_user_find().

00417 {
00418   user_t *u;
00419 
00420   /* Check the ircmask cache. */
00421   if (!hash_table_find(irchost_cache_ht, irchost, &u)) return(u);
00422 
00423   /* Look for a match in the ircmask list. We don't cache the result. */
00424   ircmask_list_find(&ircmask_list, irchost, &u);
00425   return(u);
00426 }

user_t* user_lookup_by_uid ( int  uid  ) 

Definition at line 408 of file users.c.

References hash_table_find(), and NULL.

Referenced by Egguser_New(), script_uid_to_handle(), and script_validuid().

00409 {
00410   user_t *u = NULL;
00411 
00412   hash_table_find(uid_ht, (void *)uid, &u);
00413   return(u);
00414 }

user_t* user_new ( const char *  handle  ) 

Definition at line 329 of file users.c.

References user_setting_t::extended, xml_node::name, user::nsettings, NULL, real_user_new(), user::settings, user_get_uid(), and xml_node_new().

Referenced by create_userfile(), party_plus_bot(), party_plus_obot(), party_plus_user(), script_adduser(), and terminal_init().

00330 {
00331   int uid;
00332   user_t *u;
00333 
00334   uid = user_get_uid();
00335   u = real_user_new(handle, uid);
00336   if (!u) return(NULL);
00337 
00338   /* All users have the global setting by default. */
00339   u->settings = calloc(1, sizeof(*u->settings));
00340   u->nsettings = 1;
00341   u->settings[0].extended = xml_node_new();
00342   u->settings[0].extended->name = strdup("extended");
00343 
00344   return(u);
00345 }

int user_rand_pass ( char *  buf,
int  bufsize 
)

Definition at line 775 of file users.c.

Referenced by create_userfile(), and user_set_pass().

00776 {
00777   int i, c;
00778 
00779   bufsize--;
00780   if (!buf || bufsize <= 0) return(-1);
00781   for (i = 0; i < bufsize; i++) {
00782     c = (random() + (random() >> 16) + (random() >> 24)) % 62;
00783     if (c < 10) c += 48;  /* Digits. */
00784     else if (c < 36) c += 55; /* Uppercase. */
00785     else c += 61; /* Lowercase. */
00786     buf[i] = c;
00787   }
00788   buf[i] = 0;
00789   return(0);
00790 }

static int user_really_delete ( void *  client_data  )  [static]

Definition at line 347 of file users.c.

References user_setting_t::chan, user_setting_t::extended, user::handle, user::ircmasks, user::nircmasks, user::nsettings, user::settings, and xml_node_delete().

Referenced by user_delete().

00348 {
00349   int i;
00350   user_t *u = client_data;
00351   user_setting_t *setting;
00352 
00353   /* Free the ircmasks. */
00354   for (i = 0; i < u->nircmasks; i++) free(u->ircmasks[i]);
00355   if (u->ircmasks) free(u->ircmasks);
00356 
00357   /* And all of the settings. */
00358   for (i = 0; i < u->nsettings; i++) {
00359     setting = u->settings+i;
00360     xml_node_delete(setting->extended);
00361     if (setting->chan) free(setting->chan);
00362   }
00363   if (u->settings) free(u->settings);
00364   if (u->handle) free(u->handle);
00365 
00366   free(u);
00367   return(0);
00368 }

int user_save ( const char *  fname  ) 

Definition at line 261 of file users.c.

References g_uid, hash_table_walk(), xml_node::name, NULL, save_walker(), uid_wraparound, unlink_walker(), XML_INDENT, xml_node_delete(), xml_node_new(), xml_node_set_int(), and xml_save_file().

Referenced by core_shutdown_or_restart(), create_userfile(), party_save(), and script_user_save().

00262 {
00263   xml_node_t *root;
00264 
00265   root = xml_node_new();
00266   root->name = strdup("users");
00267 
00268   xml_node_set_int(g_uid, root, "next_uid", 0, 0);
00269   xml_node_set_int(uid_wraparound, root, "uid_wraparound", 0, 0);
00270   hash_table_walk(uid_ht, save_walker, root);
00271 
00272   xml_save_file((fname) ? fname : "users.xml", root, XML_INDENT);
00273 
00274   hash_table_walk(uid_ht, unlink_walker, NULL);
00275 
00276   xml_node_delete(root);
00277   return(0);
00278 }

int user_set_flags ( user_t u,
const char *  chan,
flags_t flags 
)

Definition at line 615 of file users.c.

References append_setting(), flags_t::builtin, channel_sanity_check(), check_flag_change(), get_flags(), global_sanity_check(), NULL, and flags_t::udef.

00616 {
00617   flags_t *oldflags, newflags;
00618 
00619   if (get_flags(u, chan, &oldflags)) {
00620     append_setting(u, chan, NULL, NULL);
00621     if (get_flags(u, chan, &oldflags)) return -1;
00622   }
00623   newflags.builtin = flags->builtin;
00624   newflags.udef = flags->udef;
00625   if (check_flag_change(u, chan, oldflags, &newflags)) return(0);
00626   oldflags->builtin = newflags.builtin;
00627   oldflags->udef = newflags.udef;
00628   if (chan)
00629     channel_sanity_check(oldflags);
00630   else
00631     global_sanity_check(oldflags);
00632   return(0);
00633 }

int user_set_flags_str ( user_t u,
const char *  chan,
const char *  flags 
)

Definition at line 635 of file users.c.

References append_setting(), flags_t::builtin, channel_sanity_check(), check_flag_change(), flag_merge_str(), get_flags(), global_sanity_check(), NULL, and flags_t::udef.

Referenced by create_userfile(), party_chattr(), party_plus_bot(), party_plus_obot(), script_setflags(), SetFlags(), and terminal_init().

00636 {
00637   flags_t *oldflags, newflags;
00638 
00639   if (get_flags(u, chan, &oldflags)) {
00640     append_setting(u, chan, NULL, NULL);
00641     if (get_flags(u, chan, &oldflags)) return(-1);
00642   }
00643   newflags.builtin = oldflags->builtin;
00644   newflags.udef = oldflags->udef;
00645   flag_merge_str(&newflags, flags);
00646   if (check_flag_change(u, chan, oldflags, &newflags)) return(0);
00647   oldflags->builtin = newflags.builtin;
00648   oldflags->udef = newflags.udef;
00649   if (chan)
00650     channel_sanity_check(oldflags);
00651   else
00652     global_sanity_check(oldflags);
00653   return(0);
00654 }

int user_set_pass ( user_t u,
const char *  pass 
)

Definition at line 743 of file users.c.

References MD5_Final(), MD5_Hex(), MD5_Init(), MD5_Update(), NULL, user_get_setting(), user_rand_pass(), and user_set_setting().

Referenced by create_userfile(), party_chpass(), party_newpass(), and SetPass().

00744 {
00745   char hashhex[33], *salt, new_salt[33];
00746   unsigned char hash[16];
00747   MD5_CTX ctx;
00748 
00749   user_get_setting(u, NULL, "salt", &salt);
00750   if (!salt) {
00751     salt = new_salt;
00752     user_rand_pass(salt, sizeof(new_salt));
00753     user_set_setting(u, NULL, "salt", salt);
00754   }
00755 
00756   if (!pass || !*pass) {
00757     user_set_setting(u, NULL, "pass", "none");
00758     return(1);
00759   }
00760   MD5_Init(&ctx);
00761   MD5_Update(&ctx, salt, strlen(salt));
00762   MD5_Update(&ctx, pass, strlen(pass));
00763   MD5_Final(hash, &ctx);
00764   MD5_Hex(hash, hashhex);
00765   user_set_setting(u, NULL, "pass", hashhex);
00766   return(0);
00767 }

int user_set_setting ( user_t u,
const char *  chan,
const char *  setting,
const char *  value 
)

Definition at line 699 of file users.c.

References bind_check(), BIND_RET_BREAK, egg_msprintf(), find_setting(), user::handle, NULL, and xml_node_set_str().

Referenced by got_handshake(), party_plus_bot(), party_plus_obot(), script_user_set(), Set(), and user_set_pass().

00700 {
00701   int r;
00702   char *change, buf[64];
00703   xml_node_t *node;
00704 
00705   change = egg_msprintf(buf, sizeof(buf), NULL, "%s %s", chan ? chan : "", setting);
00706   r = bind_check(BT_uset, NULL, change, u->handle, chan, setting, value);
00707   if (change != buf) free(change);
00708 
00709   if (r & BIND_RET_BREAK) return(0);
00710 
00711   node = find_setting(u, chan, setting, 1);
00712   return xml_node_set_str(value, node, NULL);
00713 }

int user_shutdown ( void   ) 

Definition at line 147 of file users.c.

References bind_table_del(), garbage_run(), hash_table_delete(), hash_table_walk(), NULL, and userlist_delete_walker().

Referenced by eggdrop_shutdown().

00148 {
00149   hash_table_walk(uid_ht, userlist_delete_walker, NULL);
00150 
00151   /* flush any pending user delete events */
00152   garbage_run();
00153 
00154   bind_table_del(BT_udelete);
00155   bind_table_del(BT_uset);
00156   bind_table_del(BT_uflags);
00157 
00158   hash_table_delete(irchost_cache_ht);
00159   hash_table_delete(uid_ht);
00160   hash_table_delete(handle_ht);
00161 
00162   return (0);
00163 }

void user_walk ( hash_table_node_func  callback,
void *  data 
)

Definition at line 165 of file users.c.

References hash_table_walk().

Referenced by botnet_autolink().

00166 {
00167   hash_table_walk(uid_ht, callback, data);
00168 }

static int userlist_delete_walker ( const void *  key,
void *  dataptr,
void *  client_data 
) [static]

Definition at line 387 of file users.c.

References user_delete().

Referenced by user_shutdown().

00388 {
00389   return user_delete(*(user_t **)dataptr);
00390 }


Variable Documentation

bind_table_t* BT_udelete = NULL [static]

Bind:
This flag is triggered every time a user is deleted.
Name:
udelete
Flags:
ignored
Match:
Nothing.
Parameters:
user The deleted user.
Note:
This bind is stackable.
Returns:
Any return value will be ignored.
Bug:
The flags are ignored, nothing is matched, the bind is triggered after the user was deleted.

Definition at line 116 of file users.c.

bind_table_t* BT_uflags = NULL [static]

Bind:
This flag is triggered every time the flags of a user are changed.
Name:
uflags
Flags:
ignored
Match:
"channel oldflags newflags"
Parameters:
string The user's handle.
string The channel.
string The old flags.
string The new flags.
Note:
This bind is stackable.
Returns:
The return value is broken.
Bug:
The flags are ignored, the return value is treated as if the bind is breakable, the user is passed as a string.

Definition at line 83 of file users.c.

bind_table_t* BT_uset = NULL [static]

Bind:
This flag is triggered every time a user's settings are changed.
Name:
uset
Flags:
ignored
Match:
"channel setting"
Parameters:
string The user's handle.
string The channel.
string The setting.
string The value.
Note:
This bind is stackable.
Returns:
The return value is broken.
Bug:
The flags are ignored, the return value is treated as if the bind is breakable, the user is passed as a string.

Definition at line 101 of file users.c.

int g_uid = 1 [static]

Definition at line 50 of file users.c.

Referenced by user_get_uid(), user_load(), and user_save().

hash_table_t* handle_ht = NULL [static]

Definition at line 59 of file users.c.

hash_table_t* irchost_cache_ht = NULL [static]

Definition at line 56 of file users.c.

ircmask_list_t ircmask_list = {NULL} [static]

Definition at line 65 of file users.c.

int nusers = 0 [static]

Definition at line 53 of file users.c.

Referenced by real_user_new(), user_count(), user_delete(), and user_load().

const char rcsid[] = "$Id: users.c,v 1.56 2007-05-10 00:25:07 sven Exp $" [static]

Definition at line 21 of file users.c.

hash_table_t* uid_ht = NULL [static]

Definition at line 62 of file users.c.

int uid_wraparound = 0 [static]

Definition at line 50 of file users.c.

Referenced by user_get_uid(), user_load(), and user_save().


Generated on Sun Nov 30 18:43:35 2008 for eggdrop1.9 by  doxygen 1.5.6