/*------------------------------------------------------------------ * Header file for Javelin's extended @chat system * Based on the Battletech MUSE comsystem ported to PennMUSH by Kalkin * * Why: * In the old system, channels were represented by bits set in a * 4-byte int on the db object. This had disadvantages - a limit * of 32 channels, and players could find themselves on null channels. * In addition, the old system required recompiles to permanently * add channels, since the chaninfo was in the source. * How: * Channels are a structure in a linked list. * Each channel stores a whole bunch of info, including who's * on it. * We read/write this list using a chatdb file. * We also maintain a linked list of channels that the user is * connected to on the db object, which we set up at load time. * * User interface: * @chat channel = message * +channel message * @channel/on channel [= player] (or @channel channel = on) do_channel() * @channel/off channel [= player] do_channel() * @channel/who channel do_channel() * @channel/title channel=title do_chan_title() * @channel/list do_chan_list() * @channel/add channel do_chan_admin() * @channel/priv channel = <privlist> do_chan_admin() * Privlist being: wizard, admin, private, moderated, etc. * @channel/joinlock channel = lock * @channel/speaklock channel = lock * @channel/modlock channel = lock * @channel/delete channel * @channel/quiet channel = yes/no * @channel/wipe channel * *------------------------------------------------------------------*/ #ifndef __EXTCHAT_H #define __EXTCHAT_H #ifdef CHAT_SYSTEM #define CU_TITLE_LEN 80 /* This is a user - someone who's listening on a chat channel */ struct chanuser { dbref who; long int type; char title[CU_TITLE_LEN]; struct chanuser *next; }; typedef struct chanuser CHANUSER; /* Flags and macros for channel users */ #define CU_QUIET 0x1 /* Do not hear connection messages */ #define CU_HIDE 0x2 /* Do not appear on the user list */ #define CU_GAG 0x4 /* Do not hear any messages */ #define CU_DEFAULT_FLAGS 0x0 #define CUdbref(u) ((u)->who) #define CUtype(u) ((u)->type) #define CUtitle(u) ((u)->title) #define CUnext(u) ((u)->next) #define Chanuser_Quiet(u) (CUtype(u) & CU_QUIET) #define Chanuser_Hide(u) ((CUtype(u) & CU_HIDE) || hidden(CUdbref(u))) #define Chanuser_Gag(u) (CUtype(u) & CU_GAG) /* This is a chat channel */ #define CHAN_NAME_LEN 31 #define CHAN_TITLE_LEN 256 struct channel { char name[CHAN_NAME_LEN]; /* Channel name */ char title[CHAN_TITLE_LEN]; /* Channel description */ long int type; /* Channel flags */ long int cost; /* Anyone can make a channel, but this is the cost */ long int creator; /* This is who paid the cost for the channel */ long int num_users; /* Number of connected users */ long int max_users; /* Maximum allocated users */ struct chanuser *users; /* Linked list of who is on */ long int num_messages; /* How many messages handled by this chan since startup */ struct boolexp *joinlock; /* Who may join */ struct boolexp *speaklock; /* Who may speak */ struct boolexp *modifylock; /* Who may change things and boot people */ struct boolexp *seelock; /* Who can see this in a list */ struct boolexp *hidelock; /* Who may hide from view */ struct channel *next; /* Next in linked list */ }; typedef struct channel CHAN; struct chanlist { CHAN *chan; struct chanlist *next; }; typedef struct chanlist CHANLIST; #define Chanlist(x) db[(x)].channels /* Channel type flags and macros */ #define CHANNEL_PLAYER 0x1 /* Players may join */ #define CHANNEL_OBJECT 0x2 /* Objects may join */ #define CHANNEL_DISABLED 0x4 /* Channel is turned off */ #define CHANNEL_QUIET 0x8 /* No broadcasts connect/disconnect */ #define CHANNEL_ADMIN 0x10 /* Wizard and royalty only ok */ #define CHANNEL_WIZARD 0x20 /* Wizard only ok */ #define CHANNEL_CANHIDE 0x40 /* Can non-DARK Wizards hide here? */ #define CHANNEL_DEFAULT_FLAGS (CHANNEL_PLAYER) #define CL_JOIN 0x1 #define CL_SPEAK 0x2 #define CL_MOD 0x4 #define CL_SEE 0x8 #define CL_HIDE 0x10 #define CHANNEL_COST (options.chan_cost) #define MAX_PLAYER_CHANS (options.max_player_chans) #define MAX_CHANNELS (options.max_channels) #define ChanName(c) ((c)->name) #define ChanType(c) ((c)->type) #define ChanTitle(c) ((c)->title) #define ChanCreator(c) ((c)->creator) #define ChanCost(c) ((c)->cost) #define ChanNumUsers(c) ((c)->num_users) #define ChanMaxUsers(c) ((c)->max_users) #define ChanUsers(c) ((c)->users) #define ChanNext(c) ((c)->next) #define ChanNumMsgs(c) ((c)->num_messages) #define ChanJoinLock(c) ((c)->joinlock) #define ChanSpeakLock(c) ((c)->speaklock) #define ChanModLock(c) ((c)->modifylock) #define ChanSeeLock(c) ((c)->seelock) #define ChanHideLock(c) ((c)->hidelock) #define Channel_Quiet(c) (ChanType(c) & CHANNEL_QUIET) #define Channel_Object(c) (ChanType(c) & CHANNEL_OBJECT) #define Channel_Player(c) (ChanType(c) & CHANNEL_PLAYER) #define Channel_Disabled(c) (ChanType(c) & CHANNEL_DISABLED) #define Channel_Wizard(c) (ChanType(c) & CHANNEL_WIZARD) #define Channel_Admin(c) (ChanType(c) & CHANNEL_ADMIN) #define Channel_CanHide(c) (ChanType(c) & CHANNEL_CANHIDE) #define Chan_Ok_Type(c,o) \ (((Typeof(o) == TYPE_PLAYER) && Channel_Player(c)) || \ ((Typeof(o) == TYPE_THING) && Channel_Object(c))) #define Chan_Can(p,t) \ (!(t & CHANNEL_DISABLED) && (!(t & CHANNEL_WIZARD) || Wizard(p)) && \ (!(t & CHANNEL_ADMIN) || Hasprivs(p) || (Powers(p) & CHAT_PRIVS))) /* Who can change channel privileges to type t */ #define Chan_Can_Priv(p,t) (Wizard(p) || Chan_Can(p,t)) #define Chan_Can_Access(c,p) (Chan_Can(p,ChanType(c))) #define Chan_Can_Join(c,p) \ (Chan_Can_Access(c,p) && \ (eval_boolexp(p,ChanJoinLock(c),p,0,"ChanJoinlock"))) #define Chan_Can_Speak(c,p) \ (Chan_Can_Access(c,p) && \ (eval_boolexp(p,ChanSpeakLock(c),p,0,"ChanSpeaklock"))) #define Chan_Can_Modify(c,p) \ (Wizard(p) || (ChanCreator(c) == (p)) || \ (!Guest(p) && Chan_Can_Access(c,p) && \ (eval_boolexp(p,ChanModLock(c),p,0,"ChanModlock")))) #define Chan_Can_See(c,p) \ (Wizard(p) || (Chan_Can_Access(c,p) && \ (eval_boolexp(p,ChanSeeLock(c),p,0,"ChanSeelock")))) #define Chan_Can_Hide(c,p) \ (Can_Hide(p) || (Channel_CanHide(c) && Chan_Can_Access(c,p) && \ (eval_boolexp(p,ChanHideLock(c),p,0,"ChanHidelock")))) #define Chan_Can_Nuke(c,p) (Wizard(p) || (ChanCreator(c) == (p))) #define Chan_Can_Decomp(c,p) (See_All(p) || (ChanCreator(c) == (p))) /* For use in channel matching */ #define CMATCH_NONE 0 #define CMATCH_EXACT 1 #define CMATCH_PARTIAL 2 #define CMATCH_AMBIG 3 #define CMATCHED(i) (((i) == CMATCH_EXACT) | ((i) == CMATCH_PARTIAL)) /* Some globals */ extern int num_channels; extern void channel_broadcast _((CHAN *channel, int flags, const char *fmt,...)); extern CHANUSER *onchannel _((dbref who, CHAN *c)); extern void init_chatdb _((void)); extern int load_chatdb _((FILE * fp)); extern int save_chatdb _((FILE * fp)); extern void do_cemit _((dbref player, const char *name, const char *msg)); extern void do_chan_user_flags _((dbref player, char *name, const char *isyn, int flag, int silent)); extern void do_chan_wipe _((dbref player, const char *name)); extern void do_chan_lock _((dbref player, const char *name, const char *lockstr, int whichlock)); extern void do_chan_what _((dbref player, const char *partname)); extern void do_chan_desc _((dbref player, const char *name, const char *title)); extern void do_chan_title _((dbref player, const char *name, const char *title)); #endif /* CHAT_SYSTEM */ #endif /* __EXTCHAT_H */