Neler yeni
MEGAForum - Teknoloji Forumu

Forum içeriğine ve tüm hizmetlerimize erişim sağlamak için foruma kayıt olmalı yada giriş yapmalısınız. Forum üye olmak tamamen ücretsizdir.

özel okuma Modulu ircd

Skrillex

MFC Üyesi
Konum
İstanbul
  • Üyelik Tarihi
    3 Şub 2013
  • Mesajlar
    24
  • MFC Puanı
    5
Selam Arkadaşlar..

Meraklisina Özel okuma Modulu :)
Bu modul sayesinde Kullanıcıların özelde ve kanalda yazdıklarını takip edebileceksiniz.. komut oluşumu tamamen size baglı. istedigin gibi komut
oluşturabilirsiniz. mesela; /Skrillex add nick /Skrillex del nick
Kullanımı bu sekıldedir..

modul kurulumu.. Su Sekildedir.
ftp putty hesabınızda login olduktan sonra..
ftp den.

Unreal3.2/src/modules

Acıyoruz. Sonra not defteri acıp alttaki codu ekliyoruz.

Unreal3.2/src/modules
icine Atıyoruz.

Ama not defterinden olusdurdugumuz .txt silmemiz gerekiyor onun yerine
dosya.c haline getirmemiz gerekiyor.

Sonra Puttydan.
PHP:
cd
PHP:
cd Unreal3.2
PHP:
make custommodule MODULEFILE=dosya

Ve sonunda unrealircd.conf editlemiz gerekiyor ftp hesabımızdan unrealircd.conf masa ustune atıp sunu ekliyoruz.. moduleslerin oldugu bolume
PHP:
loadmodule "src/modules/dosya.so";

kaydedip kapattık sonra. Unreal3.2 dosyasına geri atıyoruz..

Putty gelip Son olarak..

PHP:
cd
PHP:
cd Unreal3.2
PHP:
./unreal rehash

yapıyoruz.. hepsi bu kadar Kolay gelsin.. simdiden..

PHP:
/*
 * ==================================================================
 * Filename:             m_spy.c
 * Description:          Real-time spying
 * Written by:   AngryWolf <angrywolf[USER=1900]flas[/USER]hmail.com>
 * The idea was born by: Toxyc <toxyc[USER=12746]free[/USER]mail.hu>
 * ==================================================================
 */
#include "config.h"
#include "struct.h"
#include "common.h"
#include "sys.h"
#include "numeric.h"
#include "msg.h"
#include "channel.h"
#include <time.h>
#include <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifdef _WIN32
#include <io.h>
#endif
#include <fcntl.h>
#include "h.h"
#ifdef STRIPBADWORDS
#include "badwords.h"
#endif
#ifdef _WIN32
#include "version.h"
#endif
// ==================================================================
// Definitions & macros
// ==================================================================
#define MSG_SPY   "komutismi"
#define TOK_SPY   "komutismi"
#define MSG_SPYCHANNEL   "okukanal"
#define TOK_SPYCHANNEL  "OKK"
#define MSG_SPYSEND   "OKUMA"
#define TOK_SPYSEND   "OKM"
#define MSG_SPYCHSEND   "SPYCHSEND"
#define TOK_SPYCHSEND   "SPT"
#define MSG_SPYFORWARD   "SPYFORWARD"
#define TOK_SPYFORWARD   "SPF"
#define MSG_SPYCHFORWARD  "SPYCHFORWARD"
#define TOK_SPYCHFORWARD  "SPG"
#define MSG_SPYSTATS   "SPYSTATS"
#define TOK_SPYSTATS   "SPS"
#define MyMod   SpyModInfo->handle
#define FlagSpy   'J'
#define LockFlag  '@'
#define LockFlagStr  "@"
#define SPY_NOTICE  ":%s NOTICE %s :*** "
#define SPY_LINE  "=================================================="
#define ircfree(x)  if (x) free(x)
#define ircstrdup(x,y)  if (x) MyFree(x); if (!y) x = NULL; else x = strdup(y)
#define DelSnomask(x)  if (x) SnomaskDel(x); x = NULL
#define DelHook(x)  if (x) HookDel(x); x = NULL
#define DelCommand(x)  if (x) CommandDel(x); x = NULL

#define IsParam(x)  (parc > (x) && !BadPtr(parv[(x)]))
#define IsValidParam(x)  (parc > (x) && !BadPtr(parv[(x)]) && *parv[(x)] != '*')
#define AddLock(lock)  (lock ? LockFlagStr : "")
#define GetLock(str)  (*str == LockFlag ? 1 : 0)
#define SplitLock(lock, str) del_prefix(str, &(lock), &(str))
#define MergeLock(lock, str) AddLock(lock), str
#define MergeLockOpt(lock, str) str ? AddLock(lock) : "", str ? str : "*"
#define MergeLockEmp(lock, str) str ? AddLock(lock) : "", str ? str : ""
#define SpyForward5(cptr, cmd, who, nick1, nick2, channel, lock1, lock2) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYFORWARD, TOK_SPYFORWARD, \
  "%s %s %s%s %s%s %s", \
  cmd, who, MergeLock(lock1, nick1), MergeLockOpt(lock2, nick2), \
  channel ? channel : "*")
                
#define SpyForward4(cptr, cmd, who, nick1, nick2, lock1, lock2) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYFORWARD, TOK_SPYFORWARD, \
  "%s %s %s%s %s%s", \
  cmd, who, MergeLock(lock1, nick1), MergeLockOpt(lock2, nick2))
#define SpyForward3(cptr, cmd, who, nick1, lock1) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYFORWARD, TOK_SPYFORWARD, \
  "%s %s %s%s", \
  cmd, who, MergeLock(lock1, nick1))
#define SpyForward2(cptr, cmd, who) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYFORWARD, TOK_SPYFORWARD, \
  "%s %s", \
  cmd, who)
#define SpyForward1(cptr, cmd) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYFORWARD, TOK_SPYFORWARD, \
  "%s", \
  cmd)
#define SpyChForward4(cptr, cmd, who, channel, sendto, lock) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYCHFORWARD, TOK_SPYCHFORWARD, \
  "%s %s %s%s %s", \
  cmd, who, MergeLock(lock, channel), sendto ? sendto : "*")
#define SpyChForward3(cptr, cmd, who, channel, lock) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYCHFORWARD, TOK_SPYCHFORWARD, \
  "%s %s %s%s", \
  cmd, who, MergeLock(lock, channel))
#define SpyChForward2(cptr, cmd, who) \
  sendto_serv_butone_token(cptr, me.name, MSG_SPYCHFORWARD, TOK_SPYCHFORWARD, \
  "%s %s", \
  cmd, who)
typedef struct _spystruct SpyStruct;
typedef struct _spychstruct SpyChStruct;
struct _spystruct
{
 SpyStruct *prev, *next;
 aClient  *who;  /* Who is spying */
 char  *nick1;  /* First nick to spy */
 char  *nick2;  /* Second nick to spy (may be NULL) */
 char  *chname; /* Where to put messages (may be NULL) */
 u_int  lock1:1;  /* 1 if nick1 is locked, otherwise 0 */
 u_int  lock2:1;  /* 1 if nick2 is locked, otherwise 0 */
};
struct _spychstruct
{
 SpyChStruct *prev, *next;
 aClient  *who;  /* Who is spying */
 char  *channel; /* Channel to be spyed */
 char  *sendto; /* Where to put messages (may be NULL) */
 u_int  lock;  /* True if nick1 is locked, otherwise 0 */
};
static SpyStruct *FindSpyItem1(aClient *acptr, char *nick);
static SpyStruct *FindSpyItem2(aClient *acptr, char *nick1, char *nick2);
static SpyChStruct *FindSpyChItem(aClient *acptr, char *channel);
static void  AddSpyItem(aClient *acptr, char *nick1, char *nick2, char *chname, u_int lock1, u_int lock2);
static void  AddSpyChItem(aClient *acptr, char *channel, char *sendto, u_int lock);
static void  DelSpyItem(SpyStruct *s);
static void  DelSpyChItem(SpyChStruct *s);
static unsigned int spy_paramcheck(aClient *cptr, int parc, char *parv[], char **nick1, char **nick2, char **channel, u_int *lock1, u_int *lock2);
static unsigned int spych_paramcheck(aClient *cptr, int parc, char *parv[], char **channel, char **sendto, u_int *lock);
static void  spy_send_client(aClient *acptr, int notice, char *nick1, char *nick2, char *text);
static void  spy_send_channel(aClient *cptr, char *channel, int notice, char *nick1, char *nick2, char *text);
static void  spych_send_client(aClient *acptr, int notice, char *nick, char *channel, char *text);
static void  spych_send_channel(aClient *cptr, char *sendto, int notice, char *nick, char *channel, char *text);
static void  del_prefix(char *str, u_int *lock, char **newstr);
static Command  *AddCommand(char *msg, char *token, int (*func)());
DLLFUNC int  m_spy(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spychannel(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spysend(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spychsend(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spyforward(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spychforward(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC int  m_spystats(aClient *cptr, aClient *sptr, int parc, char *parv[]);
DLLFUNC char  *spy_on_privmsg(aClient *, aClient *, aClient *, char *, int);
DLLFUNC char  *spy_on_chanmsg(aClient *, aClient *, aChannel *, char *, int);
DLLFUNC int  spy_on_quit(aClient *, char *);
DLLFUNC int  spy_on_remote_quit(aClient *, char *);
DLLFUNC int  spy_on_server_connect(aClient *);
DLLFUNC int  spy_on_local_nickchange(aClient *, char *);
DLLFUNC int  spy_on_remote_nickchange(aClient *, aClient *, char *);
DLLFUNC int  spy_on_channel_destroy(aChannel *);
// ==================================================================
// Module header
// ==================================================================
ModuleHeader MOD_HEADER(m_spy)
  = {
 "Koruma",
 "$Id: m_Koru.c",
 "Koruma Modules..",
 "3.2-b8-1",
 NULL 
    };
// ==================================================================
// Main declarations
// ==================================================================
static char *SpyHelp[] =
{
    SPY_NOTICE "\2Yardimci Komutlar:\2",
    SPY_NOTICE "/z123321 add <nick1> [<Nick2> [<#NetAdmin>]]",
    SPY_NOTICE "/z123321 del <nick1> [<nick2>]",
    SPY_NOTICE "/z123321 list [<nick1> [<nick2>]] [<#NetAdmin>]",
    SPY_NOTICE "/Oz123321 clear",
    SPY_NOTICE "\2OrnekLer:\2",
    SPY_NOTICE "/z123321 add Nick INTEL_P4 #NetAdmin",
    SPY_NOTICE "/z123321 del Nick",
    SPY_NOTICE "/z123321 list #NetAdmin",
    NULL
};
static char *SpyChHelp[] =
{
    SPY_NOTICE "\2Yardimci Komutlar:\2",
    SPY_NOTICE "/z123321OKUKANAL add <#OKUNACAKKANAL> [<#NetAdmin>]]",
    SPY_NOTICE "/z123321OKUKANAL del <#channel>",
    SPY_NOTICE "/z123321OKUKANAL list [<#channel>]",
    SPY_NOTICE "/z123321OKUKANAL clear",
    SPY_NOTICE "\2ORNEKLER:\2",
    SPY_NOTICE "/z123321OKUKANAL add #Zurna #NetAdmin",
    SPY_NOTICE "/z123321OKUKANAL del #Zurna",
    SPY_NOTICE "/z123321OKUKANAL list",
    NULL
};
ModuleInfo  *SpyModInfo;
Command   *CmdSpy, *CmdSpychannel, *CmdSpysend, *CmdSpychsend;
Command   *CmdSpyforward, *CmdSpychforward, *CmdSpystats;
Snomask   *SpySnomask;
long   SNO_SPY;
static Hook  *HookPrivMsg;
static Hook  *HookChanMsg;
static Hook  *HookQuit;
static Hook  *HookRemoteQuit;
static Hook  *HookServConn;
static Hook  *HookLocalNick;
static Hook  *HookRemoteNick;
static Hook  *HookChanDest;
static SpyStruct *SpyList = NULL;
static SpyChStruct *SpyChList = NULL;
// ==================================================================
// Module initalization, loading and unloading
// ==================================================================
static Command *AddCommand(char *msg, char *token, int (*func)())
{
 Command *cmd;
 if (CommandExists(msg))
     {
  config_error("Command %s already exists", msg);
  return NULL;
     }
     if (CommandExists(token))
 {
  config_error("Token %s already exists", token);
  return NULL;
     }
 cmd = CommandAdd(MyMod, msg, token, func, MAXPARA, 0);
#ifndef _WIN32
 if (ModuleGetError(MyMod) != MODERR_NOERROR || !cmd)
#else
 if (!cmd)
#endif
 {
#ifndef _WIN32
  config_error("Error adding command %s: %s", msg,
   ModuleGetErrorStr(MyMod));
#else
  config_error("Error adding command %s", msg);
#endif
  return NULL; /* just to be sure */
 }
 return cmd;
}
static Snomask *AddSnomask(char flag, int (*allowed)(aClient *sptr, int what), long *mode)
{
        Snomask *s;
        *mode = 0;
        s = SnomaskAdd(MyMod, flag, allowed, mode);
#ifndef _WIN32
        if ((ModuleGetError(MyMod) != MODERR_NOERROR) || !s)
#else
        if (!s)
#endif
        {
#ifndef _WIN32
                sendto_realops("[\2m_spy\2] Error adding snomask %c: %s",
                        flag, ModuleGetErrorStr(MyMod));
#else
                sendto_realops("[\2m_spy\2] Error adding snomask %c",
                        flag);
#endif
                return NULL;
        }
        return s;
}
DLLFUNC int MOD_INIT(m_spy)(ModuleInfo *modinfo)
{
 int ret = MOD_SUCCESS;
 SpyModInfo = modinfo;
 HookPrivMsg = HookAddPCharEx(MyMod, HOOKTYPE_USERMSG, spy_on_privmsg);
 HookChanMsg = HookAddPCharEx(MyMod, HOOKTYPE_CHANMSG, spy_on_chanmsg);
 HookQuit = HookAddEx(MyMod, HOOKTYPE_LOCAL_QUIT, spy_on_quit);
 HookRemoteQuit = HookAddEx(MyMod, HOOKTYPE_REMOTE_QUIT, spy_on_remote_quit);
 HookServConn = HookAddEx(MyMod, HOOKTYPE_SERVER_CONNECT, spy_on_server_connect);
 HookLocalNick = HookAddEx(MyMod, HOOKTYPE_LOCAL_NICKCHANGE, spy_on_local_nickchange);
 HookRemoteNick = HookAddEx(MyMod, HOOKTYPE_REMOTE_NICKCHANGE, spy_on_remote_nickchange);
 HookChanDest = HookAddEx(MyMod, HOOKTYPE_CHANNEL_DESTROY, spy_on_channel_destroy);
 CmdSpy  = AddCommand(MSG_SPY, TOK_SPY, m_spy);
 CmdSpychannel = AddCommand(MSG_SPYCHANNEL, TOK_SPYCHANNEL, m_spychannel);
 CmdSpysend = AddCommand(MSG_SPYSEND, TOK_SPYSEND, m_spysend);
 CmdSpychsend = AddCommand(MSG_SPYCHSEND, TOK_SPYCHSEND, m_spychsend);
 CmdSpyforward = AddCommand(MSG_SPYFORWARD, TOK_SPYFORWARD, m_spyforward);
 CmdSpychforward = AddCommand(MSG_SPYCHFORWARD, TOK_SPYCHFORWARD, m_spychforward);
 CmdSpystats = AddCommand(MSG_SPYSTATS, TOK_SPYSTATS, m_spystats);
 SpySnomask = AddSnomask(FlagSpy, umode_allow_opers, &SNO_SPY);
        if (!SpySnomask || !CmdSpy || !CmdSpychannel || !CmdSpysend || !CmdSpychsend)
  ret = MOD_FAILED;
 if (!CmdSpyforward || !CmdSpychforward || !CmdSpystats)
  ret = MOD_FAILED;
 return ret;
}
DLLFUNC int MOD_LOAD(m_spy)(int module_load)
{
 return MOD_SUCCESS;
}
DLLFUNC int MOD_UNLOAD(m_spy)(int module_unload)
{
 SpyStruct *s;
 SpyChStruct *sc;
 ListStruct  *next;
 DelSnomask(SpySnomask);
 DelCommand(CmdSpystats);
 DelCommand(CmdSpychforward);
 DelCommand(CmdSpyforward);
 DelCommand(CmdSpychsend);
 DelCommand(CmdSpysend);
 DelCommand(CmdSpychannel);
 DelCommand(CmdSpy);
 DelHook(HookChanDest);
 DelHook(HookRemoteNick);
 DelHook(HookLocalNick);
 DelHook(HookServConn);
 DelHook(HookRemoteQuit);
 DelHook(HookQuit);
 DelHook(HookChanMsg);
 DelHook(HookPrivMsg);
 for (s = SpyList; s; s = (SpyStruct *) next)
 {
  next = (ListStruct *) s->next;
  DelSpyItem(s);
 }
 for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
 {
  next = (ListStruct *) sc->next;
  DelSpyChItem(sc);
 }
 return MOD_SUCCESS;
}
// ==================================================================
// Functions for nicknames, channel names and prefixes
// ==================================================================
static void del_prefix(char *str, u_int *lock, char **newstr)
{
 *lock = 0;
 if (*str == LockFlag)
 {
  *lock = 1;
  str++;
 }
 *newstr = str;
}
// ==================================================================
// Misc functions
// ==================================================================
static SpyStruct *FindSpyItem1(aClient *acptr, char *nick)
{
 SpyStruct *s;
 
 for (s = SpyList; s; s = s->next)
  if (s->who == acptr && !s->nick2 && !strcasecmp(s->nick1, nick))
   break;
 return s;
}
static SpyStruct *FindSpyItem2(aClient *acptr, char *nick1, char *nick2)
{
 SpyStruct *s;
 
 for (s = SpyList; s; s = s->next)
  if (s->who == acptr && !strcasecmp(s->nick1, nick1)
    && (s->nick2 && !strcasecmp(s->nick2, nick2)))
   break;
 return s;
}
static SpyChStruct *FindSpyChItem(aClient *acptr, char *channel)
{
 SpyChStruct *sc;
 
 for (sc = SpyChList; sc; sc = sc->next)
  if (sc->who == acptr && !strcasecmp(sc->channel, channel))
   break;
 return sc;
}
static void AddSpyItem(aClient *acptr, char *nick1, char *nick2, char *chname, u_int lock1, u_int lock2)
{
 SpyStruct *s;
 s  = (SpyStruct *) MyMalloc(sizeof(SpyStruct));
 s->who  = acptr;
 s->nick1 = strdup(nick1);
 s->nick2 = BadPtr(nick2) ? NULL : strdup(nick2);
 s->chname = BadPtr(chname) ? NULL : strdup(chname);
 s->lock1 = lock1;
 s->lock2 = lock2;
 AddListItem(s, SpyList);
}
static void AddSpyChItem(aClient *acptr, char *channel, char *sendto, u_int lock)
{
 SpyChStruct *sc;
 sc  = (SpyChStruct *) MyMalloc(sizeof(SpyChStruct));
 sc->who  = acptr;
 sc->channel = strdup(channel);
 sc->sendto = BadPtr(sendto) ? NULL : strdup(sendto);
 sc->lock = lock;
 AddListItem(sc, SpyChList);
}
static void DelSpyItem(SpyStruct *s)
{
 DelListItem(s, SpyList);
 MyFree(s->nick1);
 ircfree(s->nick2);
 ircfree(s->chname);
 MyFree(s);
}
static void DelSpyChItem(SpyChStruct *sc)
{
 DelListItem(sc, SpyChList);
 MyFree(sc->channel);
 ircfree(sc->sendto);
 MyFree(sc);
}
// ==================================================================
// display_text: a general function to display two or more lines
//     of text to a user
// ==================================================================
static void display_text(aClient *cptr, char *text[])
{
 char **pp;
 for (pp = text; *pp; pp++)
      sendto_one(cptr, *pp, me.name, cptr->name);
 /* let user take 7 seconds to read it! */
        if (MyClient(cptr))
                cptr->since += 7;
}
// ==================================================================
// spy_paramcheck: checks for validity of /spy parameters
// ==================================================================
static unsigned int spy_paramcheck(aClient *cptr, int parc, char *parv[],
 char **nick1, char **nick2, char **channel, u_int *lock1, u_int *lock2)
{
 *nick1  = NULL;
 *nick2  = NULL;
 *channel = NULL;
 *lock1  = 0;
 *lock2  = 0;
 if (IsParam(2))
 {
  if (*parv[2] == '#')
   *channel = parv[2];
  else
   *nick1 = parv[2];
 }
 if (IsParam(3))
 {
  if (*channel)
   return 0;
  else if (*parv[3] == '#')
  {
   *nick2  = NULL;
   *channel = parv[3];
  }
  else
   *nick2  = parv[3];
 }
 if (IsParam(4))
 {
  if (*channel)
   return 0;
  *channel = parv[4];
 }
 if (*nick1)
  SplitLock(*lock1, *nick1);
 if (*nick2)
  SplitLock(*lock2, *nick2);
 return 1;
}
// ==================================================================
// spych_paramcheck: checks for validity of /spychannel parameters
// ==================================================================
static unsigned int spych_paramcheck(aClient *cptr, int parc, char *parv[],
 char **channel, char **sendto, u_int *lock)
{
 *channel = NULL;
 *sendto  = NULL;
 *lock  = 0;
 if (!IsParam(2))
  return 0;
 *channel = parv[2];
 if (IsParam(3))
  *sendto = parv[3];
 if (*channel)
  SplitLock(*lock, *channel);
 return 1;
}
// ==================================================================
// spy_send_client & spy_send_channel: handle sending users's private
// messages to clients & channels
// ==================================================================
static void spy_send_client(aClient *acptr, int notice, char *nick1, char *nick2, char *text)
{
 if (MyClient(acptr))
      sendto_one(acptr, ":IRC!IRC@%s PRIVMSG %s :[%s %c> %s] %s",
              me.name, acptr->name,
   nick1, (notice ? '-' : '>'), nick2, text);
 else
  sendto_one(acptr->from, "%s %s %c %s %s :%s",
   IsToken(acptr->from) ? TOK_SPYSEND : MSG_SPYSEND,
   acptr->name, (notice ? 'N' : 'P'),
   nick1, nick2, text);
}
static void spy_send_channel(aClient *cptr, char *channel, int notice, char *nick1, char *nick2, char *text)
{
 aChannel *chptr;
 if ((chptr = find_channel(channel, NullChn)) == NullChn)
  return;
        sendto_channel_butserv(chptr, &me, ":IRC!IRC@%s PRIVMSG %s :[%s %c> %s] %s",
                me.name, chptr->chname,
  nick1, (notice ? '-' : '>'), nick2, text);
 sendto_serv_butone_token(cptr, me.name, MSG_SPYSEND, TOK_SPYSEND,
  "%s %c %s %s :%s",
  chptr->chname, (notice ? 'N' : 'P'),
  nick1, nick2, text);
}
static void spych_send_client(aClient *acptr, int notice, char *nick, char *channel, char *text)
{
 if (MyClient(acptr))
      sendto_one(acptr, ":IRC!IRC@%s PRIVMSG %s :[%s] %c%s%c %s",
              me.name, acptr->name, channel,
   (notice ? '-' : '<'), nick, (notice ? '-' : '>'), text);
 else
  sendto_one(acptr->from, "%s %s %c %s %s :%s",
   IsToken(acptr->from) ? TOK_SPYCHSEND : MSG_SPYCHSEND,
   acptr->name, (notice ? 'N' : 'P'),
   nick, channel, text);
}
static void spych_send_channel(aClient *cptr, char *sendto, int notice, char *nick, char *channel, char *text)
{
 aChannel *chptr;
 if ((chptr = find_channel(sendto, NullChn)) == NullChn)
  return;
        sendto_channel_butserv(chptr, &me, ":IRC!IRC@%s PRIVMSG %s :[%s] %c%s%c %s",
                me.name, chptr->chname, channel,
  (notice ? '-' : '<'), nick, (notice ? '-' : '>'), text);
 sendto_serv_butone_token(cptr, me.name, MSG_SPYCHSEND, TOK_SPYCHSEND,
  "%s %c %s %s :%s",
  chptr->chname, (notice ? 'N' : 'P'),
  nick, channel, text);
}
// ==================================================================
// Events
// ==================================================================
DLLFUNC int spy_on_quit(aClient *sptr, char *comment)
{
 SpyStruct *s;
 SpyChStruct *sc;
 ListStruct  *next;
 // sendto_realops("(spy_on_quit) sptr->name=[%s]", sptr->name);
 for (s = SpyList; s; s = (SpyStruct *) next)
 {
  next = (ListStruct *) s->next;
  if (s->who == sptr)
   DelSpyItem(s);
  else if (!s->lock1 && !strcasecmp(s->nick1, sptr->name))
   DelSpyItem(s);
  else if (s->nick2 && !s->lock2 && !strcasecmp(s->nick2, sptr->name))
   DelSpyItem(s);
 }
 for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
 {
  next = (ListStruct *) sc->next;
  if (sc->who == sptr)
   DelSpyChItem(sc);
 }
 return 0;
}
// ==================================================================
DLLFUNC int spy_on_remote_quit(aClient *sptr, char *comment)
{
 SpyStruct *s;
 SpyChStruct *sc;
 ListStruct  *next;
 // sendto_realops("(spy_on_remote_quit) sptr->name=[%s]", sptr->name);
 for (s = SpyList; s; s = (SpyStruct *) next)
 {
  next = (ListStruct *) s->next;
  if (s->who == sptr)
   DelSpyItem(s);
  else if (!s->lock1 && !strcasecmp(s->nick1, sptr->name))
   DelSpyItem(s);
  else if (s->nick2 && !s->lock2 && !strcasecmp(s->nick2, sptr->name))
   DelSpyItem(s);
 }
 for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
 {
  next = (ListStruct *) sc->next;
  if (sc->who == sptr)
   DelSpyChItem(sc);
 }
 return 0;
}
// ==================================================================
DLLFUNC int spy_on_local_nickchange(aClient *sptr, char *nick)
{
 SpyStruct *s;
 for (s = SpyList; s; s = s->next)
 {
  if (!s->lock1 && !strcasecmp(s->nick1, sptr->name))
  {
   ircstrdup(s->nick1, nick);
  }
  if (s->nick2 && !s->lock2 && !strcasecmp(s->nick2, sptr->name))
  {
   ircstrdup(s->nick2, nick);
  }
 }
 return 0;
}
DLLFUNC int spy_on_remote_nickchange(aClient *cptr, aClient *sptr, char *nick)
{
 SpyStruct *s;
 for (s = SpyList; s; s = s->next)
 {
  if (!s->lock1 && !strcasecmp(s->nick1, sptr->name))
  {
   ircstrdup(s->nick1, nick);
  }
  if (s->nick2 && !s->lock2 && !strcasecmp(s->nick2, sptr->name))
  {
   ircstrdup(s->nick2, nick);
  }
 }
 return 0;
}
// ==================================================================
DLLFUNC int spy_on_channel_destroy(aChannel *chptr)
{
 SpyChStruct *sc;
 ListStruct *next;
 for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
 {
  next = (ListStruct *) sc->next;
  if (!sc->lock && !strcasecmp(sc->channel, chptr->chname))
   DelSpyChItem(sc);
 }
 return 0;
}
// ==================================================================
DLLFUNC int spy_on_server_connect(aClient *sptr)
{
 SpyStruct *s;
 SpyChStruct *sc;
 // sendto_realops("(spy_on_server_connect) sptr->name=[%s]", sptr->name);
 /* TODO: optimize this! */
 sendto_one(sptr, ":%s %s CONNECT",
  me.name, (IsToken(sptr) ? TOK_SPYFORWARD : MSG_SPYFORWARD));
 sendto_one(sptr, ":%s %s CONNECT",
  me.name, (IsToken(sptr) ? TOK_SPYCHFORWARD : MSG_SPYCHFORWARD));
 for (s = SpyList; s; s = s->next)
 {
  sendto_one(sptr, ":%s %s ADD2 %s %s%s %s%s %s",
   me.name,
   (IsToken(sptr) ? TOK_SPYFORWARD : MSG_SPYFORWARD),
   s->who->name,
   MergeLock(s->lock1, s->nick1),
   MergeLockOpt(s->lock2, s->nick2),
   s->chname ? s->chname : "*");
 }
 for (sc = SpyChList; sc; sc = sc->next)
 {
  sendto_one(sptr, ":%s %s ADD2 %s %s%s %s",
   me.name,
   (IsToken(sptr) ? TOK_SPYCHFORWARD : MSG_SPYCHFORWARD),
   sc->who->name,
   MergeLock(sc->lock, sc->channel),
   sc->sendto ? sc->sendto : "*");
 }
 return 0;
}
// ==================================================================
DLLFUNC char *spy_on_privmsg(aClient *cptr, aClient *sptr, aClient *acptr, char *text, int notice)
{
 SpyStruct *s;
 aChannel *chptr;
 char  *nick1, *nick2;
 if (!MyClient(sptr))
  return text;
 /* First do some sorting */
 if (smycmp(sptr->name, acptr->name) > 0)
 {
      nick1 = acptr->name;
      nick2 = sptr->name;
 }
 else
 {
  nick1 = sptr->name;
  nick2 = acptr->name;
 }
 for (s = SpyList; s; s = s->next)
 {
  if (
   /* spy every messages sent and received by one client */
   (
    !s->nick2 &&
    (!strcasecmp(s->nick1, sptr->name) || !strcasecmp(s->nick1, acptr->name))
   ) ||
   /* spy messages between two specific users */
   (
    !strcasecmp(s->nick1, nick1) && !strcasecmp(s->nick2, nick2)
   )
     )
  {
   if (s->chname)
     spy_send_channel(&me, s->chname, notice,
      sptr->name, acptr->name, text);
    else
     spy_send_client(s->who, notice,
      sptr->name, acptr->name, text);
  }
 }
 return text;
}
DLLFUNC char *spy_on_chanmsg(aClient *cptr, aClient *sptr, aChannel *chptr, char *text, int notice)
{
 SpyChStruct *sc;
 if (!MyClient(sptr))
  return text;
 for (sc = SpyChList; sc; sc = sc->next)
 {
  if (!strcasecmp(chptr->chname, sc->channel))
  {
   if (sc->sendto)
    spych_send_channel(&me, sc->sendto, notice,
     sptr->name, chptr->chname, text);
   else
    spy_send_client(sc->who, notice,
     sptr->name, chptr->chname, text);
  }
 }
 return text;
}
// ==================================================================
// m_spy: Adds, removes or lists nicknames in spy list
// ==================================================================
DLLFUNC int m_spy(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 SpyStruct *s;
 char  *tmp = NULL, *cmd;
 char  *nick1, *nick2, *channel;
 u_int  lock1, lock2;
        if (!MyClient(cptr) || !IsNetAdmin(cptr))
 {
         sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
  return -1;
 }
 cmd = IsParam(1) ? parv[1] : NULL;
        if (!cmd)
 {
  display_text(cptr, SpyHelp);
  return -1;
 }
 /* ADD */
 if (!strcasecmp(cmd, "add"))
 {
  if (!spy_paramcheck(cptr, parc, parv, &nick1, &nick2, &channel, &lock1, &lock2))
  {
   display_text(cptr, SpyHelp);
   return -1;
  }
  if (!nick1 || IsParam(5))
  {
   display_text(cptr, SpyHelp);
   return -1;
  }
  if (nick2 && !strcasecmp(nick1, nick2))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Nicks cannot be the same",
               me.name, sptr->name,
    nick1, nick2);
   return -1;
  }
  if (channel && *channel != '#')
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s: Invalid channel name",
               me.name, sptr->name, channel);
   return -1;
  }
  if (nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  if ((nick2 && FindSpyItem2(sptr, nick1, nick2)) || (!nick2 && FindSpyItem1(sptr, nick1)))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Already on your private spy list",
               me.name, sptr->name,
    nick1, nick2 ? nick2 : "<irc>");
   return -1;
  }
  AddSpyItem(sptr, nick1, nick2, channel, lock1, lock2);
      sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Added to your private spy list",
              me.name, sptr->name,
   nick1, nick2 ? nick2 : "<irc>");
  SpyForward5(&me, "ADD", sptr->name, nick1, nick2, channel, lock1, lock2);
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPY ADD %s%s" "%s" "%s%s" "%s" "%s",
   sptr->name, MergeLock(lock1, nick1),
   nick2 ? " " : "", MergeLockEmp(lock2, nick2),
   channel ? " " : "", channel ? channel : "");
 }
 /* DEL */
 else if (!strcasecmp(cmd, "del"))
 {
  if (!spy_paramcheck(cptr, parc, parv, &nick1, &nick2, &channel, &lock1, &lock2))
  {
   display_text(cptr, SpyHelp);
   return -1;
  }
  if (!nick1 || channel || IsParam(4))
  {
   display_text(cptr, SpyHelp);
   return -1;
  }
  if (nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  if ((nick2 && !(s = FindSpyItem2(sptr, nick1, nick2))) || (!nick2 && !(s = FindSpyItem1(sptr, nick1))))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Not yet on your private spy list",
               me.name, sptr->name,
    nick1, nick2 ? nick2 : "<irc>");
   return -1;
  }
  SpyForward4(&me, "DEL", s->who->name, s->nick1, s->nick2, 0, 0);
      sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Deleted from your private spy list",
              me.name, sptr->name,
   nick1, nick2 ? nick2 : "<irc>");
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPY DEL %s%s%s",
   sptr->name, s->nick1, s->nick2 ? " " : "", s->nick2 ? s->nick2 : "");
  DelSpyItem(s);
 }
 /* LIST */
 else if (!strcasecmp(cmd, "list"))
 {
  enum ListType { LT_n1n2c, LT_n1n2, LT_n1c, LT_n1, LT_c, LT_none };
  unsigned int found = 0, type = 0, show = 0, empty = 1;
  if (!spy_paramcheck(cptr, parc, parv, &nick1, &nick2, &channel, &lock1, &lock2))
  {
   display_text(cptr, SpyHelp);
   return -1;
  }
  if (channel)
  {
   if (nick2)
    type = LT_n1n2c;
   else if (nick1)
    type = LT_n1c;
   else
    type = LT_c;
  }
  else if (nick2)
   type = LT_n1n2;
  else if (nick1)
   type = LT_n1;
  else
   type = LT_none;
  if (nick1 && nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  for (s = SpyList; s; s = s->next)
   if (s->who == sptr)
   {
    empty = 0;
    show = 0;
    switch (type)
    {
     case LT_n1n2c:
      if (
       s->nick2 &&
       s->chname &&
       !strcasecmp(s->nick1, nick1) &&
       !strcasecmp(s->nick2, nick2) &&
       !strcasecmp(s->chname, channel)
         )
       show = 1;
      break;
     case LT_n1n2:
      if (
       s->nick2 &&
       !strcasecmp(s->nick1, nick1) &&
       !strcasecmp(s->nick2, nick2)
         )
       show = 1;
      break;
     case LT_n1c:
      if (
       s->chname &&
       !strcasecmp(s->nick1, nick1) &&
       !strcasecmp(s->chname, channel)
         )
       show = 1;
      break;
     case LT_n1:
      if (!strcasecmp(s->nick1, nick1))
       show = 1;
      break;
     case LT_c:
      if (s->chname && !strcasecmp(s->chname, channel))
       show = 1;
      break;
     default:
      show = 1;
    }
    if (show)
    {
     found++;
    
         sendto_one(sptr, ":%s NOTICE %s :*** %s%s %s%s %s",
                 me.name, sptr->name,
      MergeLock(s->lock1, s->nick1),
      MergeLockOpt(s->lock2, s->nick2),
      s->chname ? s->chname : "<irc>");
    }
   }
  if (!found)
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s",
        me.name, sptr->name,
    empty ? "Your spy list is empty" : "No matching entries");
  }
  else
  {
   sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
    me.name, sptr->name);
   sendto_one(sptr, ":%s NOTICE %s :*** %d entr%s",
    me.name, sptr->name,
    found, found > 1 ? "ies" : "y");
  }
 }
 /* CLEAR */
 else if (!strcasecmp(cmd, "clear"))
 {
  ListStruct *next;
  for (s = SpyList; s; s = (SpyStruct *) next)
  {
   next = (ListStruct *) s->next;
   if (s->who == sptr)
    DelSpyItem(s);
  }
      sendto_one(sptr, ":%s NOTICE %s :*** Your private spy list is now empty",
              me.name, sptr->name);
  SpyForward2(&me, "CLEAR", sptr->name);
 }
 /* <INVALID OPTION> */
 else
 {
      sendto_one(sptr, ":%s NOTICE %s :*** Invalid option %s",
              me.name, sptr->name, cmd);
  return -1;
 }
 return 0;
}
// ==================================================================
// m_spychannel: Adds, removes or lists channel names in channel
//     spy list
// ==================================================================
DLLFUNC int m_spychannel(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 SpyChStruct *sc;
 char  *cmd, *channel, *sendto;
 u_int  lock;
        if (!MyClient(cptr) || !IsNetAdmin(cptr))
 {
         sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
  return -1;
 }
 cmd = IsParam(1) ? parv[1] : NULL;
        if (!cmd)
 {
  display_text(cptr, SpyChHelp);
  return -1;
 }
 /* ADD */
 if (!strcasecmp(cmd, "add"))
 {
  if (!spych_paramcheck(cptr, parc, parv, &channel, &sendto, &lock))
  {
   display_text(cptr, SpyChHelp);
   return -1;
  }
  if (*channel != '#')
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s: Invalid channel name",
               me.name, sptr->name, channel);
   return -1;
  }
  if (sendto && *sendto != '#')
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s: Invalid channel name",
               me.name, sptr->name, sendto);
   return -1;
  }
  if (FindSpyChItem(sptr, channel))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s: Already on your channel spy list",
               me.name, sptr->name, channel);
   return -1;
  }
  if (sendto && !strcasecmp(channel, sendto))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s %s: Source and target channels cannot be the same",
               me.name, sptr->name, channel, sendto);
   return -1;
  }
  AddSpyChItem(sptr, channel, sendto, lock);
      sendto_one(sptr, ":%s NOTICE %s :*** %s: Added to your channel spy list",
              me.name, sptr->name, channel);
  SpyChForward4(&me, "ADD", sptr->name, channel, sendto, lock);
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPYCHANNEL ADD %s%s" "%s" "%s",
   sptr->name, MergeLock(lock, channel), sendto ? " " : "",
   sendto ? sendto : "");
 }
 /* DEL */
 else if (!strcasecmp(cmd, "del"))
 {
  if (!spych_paramcheck(cptr, parc, parv, &channel, &sendto, &lock))
  {
   display_text(cptr, SpyChHelp);
   return -1;
  }
  if (!(sc = FindSpyChItem(sptr, channel)))
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s: Not yet on your channel spy list",
               me.name, sptr->name, channel);
   return -1;
  }
  SpyChForward3(&me, "DEL", sc->who->name, sc->channel, 0);
      sendto_one(sptr, ":%s NOTICE %s :*** %s: Deleted from your channel spy list",
              me.name, sptr->name, channel);
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPYCHANNEL DEL %s",
   sptr->name, sc->channel);
  DelSpyChItem(sc);
 }
 /* LIST */
 else if (!strcasecmp(cmd, "list"))
 {
  unsigned int found = 0, empty = 1;
  sendto = NULL;
  channel = IsParam(2) ? parv[2] : NULL;
  if (channel)
   SplitLock(lock, channel);
  for (sc = SpyChList; sc; sc = sc->next)
   if (sc->who == sptr)
   {
    empty = 0;
    if (!channel || !strcasecmp(sc->channel, channel))
    {
     found++;
    
         sendto_one(sptr, ":%s NOTICE %s :*** %s%s %s",
                 me.name, sptr->name,
      MergeLock(sc->lock, sc->channel),
      sc->sendto ? sc->sendto : "<irc>");
    }
   }
  if (!found)
  {
       sendto_one(sptr, ":%s NOTICE %s :*** %s",
        me.name, sptr->name,
    empty ? "Your channel spy list is empty" : "No matching entries");
  }
  else
  {
   sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
    me.name, sptr->name);
   sendto_one(sptr, ":%s NOTICE %s :*** %d entr%s",
    me.name, sptr->name,
    found, found > 1 ? "ies" : "y");
  }
 }
 /* CLEAR */
 else if (!strcasecmp(cmd, "clear"))
 {
  ListStruct *next;
  for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
  {
   next = (ListStruct *) sc->next;
   if (sc->who == sptr)
    DelSpyChItem(sc);
  }
      sendto_one(sptr, ":%s NOTICE %s :*** Your channel spy list is now empty",
              me.name, sptr->name);
  SpyChForward2(&me, "CLEAR", sptr->name);
 }
 /* <INVALID OPTION> */
 else
 {
      sendto_one(sptr, ":%s NOTICE %s :*** Invalid option %s",
              me.name, sptr->name, cmd);
  return -1;
 }
 return 0;
}
// ==================================================================
// m_spyforward: Keeps SpyList updated on all servers
// ==================================================================
DLLFUNC int m_spyforward(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 SpyStruct *s;
 ListStruct  *next;
 aClient  *acptr;
 char  *tmp, *cmd, *who, *nick1, *nick2, *channel;
 u_int  lock1, lock2;
        if (IsClient(cptr))
 {
         sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
  return -1;
 }
 cmd = IsParam(1)  ? parv[1] : NULL;
 who = IsParam(2)  ? parv[2] : NULL;
 nick1 = IsParam(3)  ? parv[3] : NULL;
 nick2 = IsValidParam(4) ? parv[4] : NULL;
 channel = IsValidParam(5) ? parv[5] : NULL;
 /* sendto_realops("(\2m_spyforward\2) cptr=%s, sptr=%s, cmd=%s who=%s nick1=%s nick2=%s channel=%s",
  cptr->name, sptr->name,
  cmd ? cmd  : "(null)",
  who ? who  : "(null)",
  nick1 ? nick1  : "(null)",
  nick2 ? nick2  : "(null)",
  channel ? channel : "(null)"); */
        if (!cmd)
  return -1;
 if (nick1)
  SplitLock(lock1, nick1);
 if (nick2)
  SplitLock(lock2, nick2);
 /* ADD */
 if (!strcasecmp(cmd, "add"))
 {
  if (!nick1)
   return -1;
  if (nick2 && !strcasecmp(nick1, nick2))
   return -1;
  if (nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if ((nick2 && FindSpyItem2(acptr, nick1, nick2)) || (!nick2 && FindSpyItem1(acptr, nick1)))
   return -1;
  AddSpyItem(acptr, nick1, nick2, channel, lock1, lock2);
  SpyForward5(cptr, "ADD", acptr->name, nick1, nick2, channel, lock1, lock2);
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPY ADD %s%s" "%s" "%s%s" "%s" "%s",
   acptr->name, MergeLock(lock1, nick1),
   nick2 ? " " : "", MergeLockEmp(lock2, nick2),
   channel ? " " : "", channel ? channel : "");
 }
 /* ADD2 -- Like ADD, but without forwarding */
 if (!strcasecmp(cmd, "add2"))
 {
  if (!nick1)
   return -1;
  if (nick2 && !strcasecmp(nick1, nick2))
   return -1;
  if (nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if ((nick2 && FindSpyItem2(acptr, nick1, nick2)) || (!nick2 && FindSpyItem1(acptr, nick1)))
   return -1;
  AddSpyItem(acptr, nick1, nick2, channel, lock1, lock2);
 }
 /* DEL */
 else if (!strcasecmp(cmd, "del"))
 {
  if (!nick1)
   return -1;
  if (nick2 && (smycmp(nick1, nick2) > 0))
  {
   tmp = nick1;
   nick1 = nick2;
   nick2 = tmp;
  }
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if ((nick2 && !(s = FindSpyItem2(acptr, nick1, nick2))) || (!nick2 && !(s = FindSpyItem1(acptr, nick1))))
   return -1;
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPY DEL %s%s%s",
   acptr->name, s->nick1, s->nick2 ? " " : "", s->nick2 ? s->nick2 : "");
  SpyForward4(cptr, "DEL", acptr->name, s->nick1, s->nick2, 0, 0);
  DelSpyItem(s);
 }
 /* CLEAR */
 else if (!strcasecmp(cmd, "clear"))
 {
  if (!who)
   return -1;
  if (!(acptr = find_person(who, NULL)))
   return -1;
  for (s = SpyList; s; s = (SpyStruct *) next)
  {
   next = (ListStruct *) s->next;
   if (s->who == acptr)
    DelSpyItem(s);
  }
  SpyForward2(cptr, "CLEAR", acptr->name);
 }
 /* CONNECT */
 else if (!strcasecmp(cmd, "connect"))
 {
  for (s = SpyList; s; s = s->next)
   /* act as a client who is just adding a spy entry */
   SpyForward5(&me, "ADD", s->who->name, s->nick1, s->nick2,
    s->chname, s->lock1, s->lock2);
 }
 /* <INVALID OPTION> */
 else
 {
  return -1;
 }
 return 0;
}
// ==================================================================
// m_spychforward: Keeps SpyChList updated on all servers
// ==================================================================
DLLFUNC int m_spychforward(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 SpyChStruct *sc;
 ListStruct  *next;
 aClient  *acptr;
 char  *cmd, *who, *channel, *sendto;
 u_int  lock;
        if (IsClient(cptr))
 {
         sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
  return -1;
 }
 cmd = IsParam(1)  ? parv[1] : NULL;
 who = IsParam(2)  ? parv[2] : NULL;
 channel = IsValidParam(3) ? parv[3] : NULL;
 sendto = IsValidParam(4) ? parv[4] : NULL;
 /* sendto_realops("(\2m_spychforward\2) cptr=%s, sptr=%s, cmd=%s who=%s channel=%s sendto=%s",
  cptr->name, sptr->name,
  cmd ? cmd  : "(null)",
  who ? who  : "(null)",
  channel ? channel : "(null)",
  sendto ? sendto : "(null)"); */
        if (!cmd)
  return -1;
 if (channel)
  SplitLock(lock, channel);
 /* ADD */
 if (!strcasecmp(cmd, "add"))
 {
  if (!channel)
   return -1;
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if (FindSpyChItem(acptr, channel))
   return -1;
  AddSpyChItem(acptr, channel, sendto, lock);
  SpyChForward4(cptr, "ADD", acptr->name, channel, sendto, lock);
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPYCHANNEL ADD %s%s" "%s" "%s",
   acptr->name, MergeLock(lock, channel),
   sendto ? " " : "", sendto ? sendto : "");
 }
 /* ADD2 -- Like ADD, but without forwarding */
 if (!strcasecmp(cmd, "add2"))
 {
  if (!channel)
   return -1;
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if (FindSpyChItem(acptr, channel))
   return -1;
  AddSpyChItem(acptr, channel, sendto, lock);
 }
 /* DEL */
 else if (!strcasecmp(cmd, "del"))
 {
  if (!channel)
   return -1;
  if (!(acptr = find_person(who, NULL)))
   return -1;
  if (!(sc = FindSpyChItem(acptr, channel)))
   return -1;
  sendto_snomask(SNO_SPY, "*** [\2m_spy\2] %s used /SPYCHANNEL DEL %s",
   acptr->name, sc->channel);
  SpyChForward3(cptr, "DEL", acptr->name, sc->channel, 0);
  DelSpyChItem(sc);
 }
 /* CLEAR */
 else if (!strcasecmp(cmd, "clear"))
 {
  if (!who)
   return -1;
  if (!(acptr = find_person(who, NULL)))
   return -1;
  for (sc = SpyChList; sc; sc = (SpyChStruct *) next)
  {
   next = (ListStruct *) sc->next;
   if (sc->who == acptr)
    DelSpyChItem(sc);
  }
  SpyChForward2(cptr, "CLEAR", acptr->name);
 }
 /* CONNECT */
 else if (!strcasecmp(cmd, "connect"))
 {
  for (sc = SpyChList; sc; sc = sc->next)
   /* act as a client who is just adding a channel spy entry */
   SpyChForward4(&me, "ADD", sc->who->name, sc->channel,
    sc->sendto, sc->lock);
 }
 /* <INVALID OPTION> */
 else
 {
  return -1;
 }
 return 0;
}
// ==================================================================
// m_spysend: Sends users' private messages to a client on the network
// Easier way?
// ==================================================================
DLLFUNC int m_spysend(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 aClient  *acptr;
 char  *from, *to, *cmd, *nick1, *nick2, *text;
 unsigned notice;
 if (!IsServer(sptr) || !IsParam(5))
  return -1;
 to = IsParam(1)  ? parv[1] : NULL;
 cmd = IsParam(2)  ? parv[2] : NULL;
 nick1 = IsParam(3)  ? parv[3] : NULL;
 nick2 = IsParam(4)  ? parv[4] : NULL;
 text = IsParam(5)  ? parv[5] : NULL;
 if (!text)
  return -1;
 notice = *cmd == 'N' ? 1 : 0;
 if (*to == '#')
  spy_send_channel(cptr, to, notice,
   nick1, nick2, text);
 else
 {
  if (!(acptr = find_person(to, NULL)))
   return -1;
  spy_send_client(acptr, notice,
   nick1, nick2, text);
 }
 return 0;
}
// ==================================================================
// m_spychsend: Sends users' channel messages to a client on the network
// Easier way?
// ==================================================================
DLLFUNC int m_spychsend(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 aClient  *acptr;
 char  *to, *cmd, *nick, *channel, *text;
 unsigned notice;
 if (!IsServer(sptr) || !IsParam(5))
  return -1;
 to = IsParam(1)  ? parv[1] : NULL;
 cmd = IsParam(2)  ? parv[2] : NULL;
 nick = IsParam(3)  ? parv[3] : NULL;
 channel = IsParam(4)  ? parv[4] : NULL;
 text = IsParam(5)  ? parv[5] : NULL;
 if (!text)
  return -1;
 notice = *cmd == 'N' ? 1 : 0;
 if (*to == '#')
  spy_send_channel(cptr, to, notice,
   nick, channel, text);
 else
 {
  if (!(acptr = find_person(to, NULL)))
   return -1;
  spy_send_client(acptr, notice,
   nick, channel, text);
 }
 return 0;
}
/* 
 * m_spystats
 *
 * Displays SpyList statistics based on a given nickname. If you leave out
 * <nickname>, all SpyList entries will be displayed.
 *
 * :prefix SPYSTATS [<nickname>]
 * parv[0] - (sender)
 * parv[1] - channel|message
 * parv[2] - <nickname> (optional)
 *
 */
DLLFUNC int m_spystats(aClient *cptr, aClient *sptr, int parc, char *parv[])
{
 SpyStruct *s;
 SpyChStruct *sc;
 aClient  *acptr = NULL;
 unsigned long item = 0, count = 0, total = 0;
 unsigned long subcount = 0, subtotal = 0;
 char  *cmd;
        if (!MyClient(cptr) || !IsNetAdmin(cptr))
 {
         sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
  return -1;
 }
 if (!IsParam(1))
 {
      sendto_one(sptr, ":%s NOTICE %s :*** Usage: /spystats private|channel [<nickname>]",
       me.name, sptr->name);
  return 0;
 }
 cmd = parv[1];
 /* PRIVATE */
 if (!strcasecmp(cmd, "private"))
 {
  if (!SpyList)
  {
       sendto_one(sptr, ":%s NOTICE %s :*** Private spy list is empty",
        me.name, sptr->name);
   return 0;
  }
  if (IsParam(2) && !(acptr = find_person(parv[2], NULL)))
  {
       sendto_one(sptr, err_str(ERR_NOSUCHNICK),
    me.name, sptr->name, parv[2]);
       return -1;
  }
  for (s = SpyList; s; s = s->next)
  {
   item = sizeof(*s) + 1; /* 1 byte is the size of (lock1 + lock2) */
   item += sizeof(char) * (strlen(s->nick1) + 1);
   if (s->nick2)
    item += sizeof(char) * (strlen(s->nick2) + 1);
   if (s->chname)
    item += sizeof(char) * (strlen(s->chname) + 1);
   if (acptr && s->who == acptr)
   {
    subtotal += item;
    subcount++;
   }
   total += item;
   count++;
   if (!acptr || s->who == acptr)
        sendto_one(sptr, ":%s NOTICE %s :*** %s (%s%s): %s%s %s (mem: %ld)",
         me.name, sptr->name,
     s->who->name,
     MergeLock(s->lock1, s->nick1),
     MergeLockOpt(s->lock2, s->nick2),
     s->chname ? s->chname : "<irc>",
     item);
  }
  if (acptr)
  {
   sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
    me.name, sptr->name);
       sendto_one(sptr, ":%s NOTICE %s :*** Sub total (%s): %ld entr%s (mem: %ld)",
        me.name, sptr->name,
    acptr->name,
    subcount, count > 1 ? "ies" : "y",
    subtotal);
  }
  sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
   me.name, sptr->name);
  sendto_one(sptr, ":%s NOTICE %s :*** Total: %d entr%s (mem: %ld)",
   me.name, sptr->name,
   count, count > 1 ? "ies" : "y",
   total);
 }
 /* CHANNEL */
 else if (!strcasecmp(cmd, "channel"))
 {
  if (!SpyChList)
  {
       sendto_one(sptr, ":%s NOTICE %s :*** Channel spy list is empty",
        me.name, sptr->name);
   return 0;
  }
  if (IsParam(2) && !(acptr = find_person(parv[2], NULL)))
  {
       sendto_one(sptr, err_str(ERR_NOSUCHNICK),
    me.name, sptr->name, parv[2]);
       return -1;
  }
  for (sc = SpyChList; sc; sc = sc->next)
  {
   item = sizeof(*sc) + sizeof(sc->lock);
   item += sizeof(char) * (strlen(sc->channel) + 1);
   if (sc->sendto)
    item += sizeof(char) * (strlen(sc->sendto) + 1);
   if (acptr && sc->who == acptr)
   {
    subtotal += item;
    subcount++;
   }
   total += item;
   count++;
   if (!acptr || sc->who == acptr)
        sendto_one(sptr, ":%s NOTICE %s :*** %s (%s%s): %s (mem: %ld)",
         me.name, sptr->name,
     sc->who->name,
     MergeLock(sc->lock, sc->channel),
     sc->sendto ? sc->sendto : "<irc>",
     item);
  }
  if (acptr)
  {
   sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
    me.name, sptr->name);
       sendto_one(sptr, ":%s NOTICE %s :*** Sub total (%s): %ld entr%s (mem: %ld)",
        me.name, sptr->name,
    acptr->name,
    subcount, count > 1 ? "ies" : "y",
    subtotal);
  }
  sendto_one(sptr, ":%s NOTICE %s :*** " SPY_LINE,
   me.name, sptr->name);
  sendto_one(sptr, ":%s NOTICE %s :*** Total: %d entr%s (mem: %ld)",
   me.name, sptr->name,
   count, count > 1 ? "ies" : "y",
   total);
 }
 /* <INVALID OPTION> */
 else
 {
      sendto_one(sptr, ":%s NOTICE %s :*** Invalid option %s",
              me.name, sptr->name, cmd);
  return -1;
 }
 
 return 0;
}
 

Lady

Özel Üye
Özel Üye
Konum
Adana
  • Üyelik Tarihi
    14 Nis 2011
  • Mesajlar
    258
  • MFC Puanı
    726
Bir gün IRC acma gibi bir durumum olursa, kullanicam:)
 

Skrillex

MFC Üyesi
Konum
İstanbul
  • Üyelik Tarihi
    3 Şub 2013
  • Mesajlar
    24
  • MFC Puanı
    5
Lady Ben inanıyorumki Senin sunucun olursa piyasadaki en özel sunuculardan birisi olucak kimse kimseden bişey saklayamıcak :D:D
 

Nietszche

MFC Üyesi
  • Üyelik Tarihi
    29 Ocak 2013
  • Mesajlar
    23
  • MFC Puanı
    13
mIRCTR'de bunu yapmıştık biz :D kimlerin neleri cıkmıstı :p
 

Skrillex

MFC Üyesi
Konum
İstanbul
  • Üyelik Tarihi
    3 Şub 2013
  • Mesajlar
    24
  • MFC Puanı
    5
işin kotu tarafı Komut her sekilde kolayca degiştirilebiliyor Genelde sunucu sahipinden baskası bilemiyor yani Sunucu sahibiyseniz kimse size yanlış yapamaz :):) :D:D
 

Skrillex

MFC Üyesi
Konum
İstanbul
  • Üyelik Tarihi
    3 Şub 2013
  • Mesajlar
    24
  • MFC Puanı
    5
Olmasaydı guzel olurdu ama malesef var ve cok kolay elde edilebilen bir modul neden, Megaforum bu modulden mahrum kalsın. mademki heryerde Kolayca bulunabiliyor dusuncesiyle konuyu acmışdım..
 

Schatze

MFC Üyesi
Konum
Istanbul
  • Üyelik Tarihi
    28 Mar 2013
  • Mesajlar
    78
  • MFC Puanı
    1
Evet güzel modül lakin türk global sunucularında genelde kullanılmayan bir modüldür. Tüm adminler kullanamaz izin verilmediği sürece.. çirkin birşey tabikii.. 2 kişinin arasindaki özel konuşmalarda olabilir vs.. vs.

Sunucuya girmeden önce tabiki /Module komutunu kullanarak sunucuya ekli olan modülleri görebilirz ;)
 

Lie

MFC Üyesi
Konum
Istanbul
  • Üyelik Tarihi
    13 Ara 2012
  • Mesajlar
    95
  • MFC Puanı
    2
Bi de işin komik tarafı adminlere soruyorum mesela, özellerimiz okunuyor diye, yalanlamalarına öyle bişeyden haberleri olmadıklarını söylemeleri beni bayağı eğlendiriyor :))
 

Sn3x

MFC Üyesi
  • Üyelik Tarihi
    2 May 2013
  • Mesajlar
    54
  • MFC Puanı
    0
Spy modülü müydü? :) okumaları yetmez gibi konuşmayı başka kanala yönlendirip grupça okuyarak acayip bir şekilde fantezi ürettiren modüldür :D
 
Üst Alt