1
0
mirror of https://git.FreeBSD.org/ports.git synced 2024-12-25 04:43:33 +00:00

- Update from 4.9.7 to 4.9.8

- Add unofficial patch for MSN support

PR:		ports/58869
Submitted by:	maintainer
This commit is contained in:
Vanilla I. Shu 2003-11-03 16:16:27 +00:00
parent 123ef17f95
commit c0e738018d
Notes: svn2git 2021-03-31 03:12:20 +00:00
svn path=/head/; revision=92973
42 changed files with 14204 additions and 2460 deletions

View File

@ -7,8 +7,8 @@
#
PORTNAME= centericq
PORTVERSION= 4.9.7
PORTREVISION= 3
PORTVERSION= 4.9.8
PORTREVISION= 0
CATEGORIES= net
MASTER_SITES= http://centericq.de/archive/source/releases/
@ -18,8 +18,6 @@ COMMENT= A text mode menu- and window-driven IM interface
LIB_DEPENDS= intl.5:${PORTSDIR}/devel/gettext \
iconv.3:${PORTSDIR}/converters/libiconv
BROKEN= Does not fetch, will be removed after Feb 2
USE_OPENSSL= yes
USE_GMAKE= yes
GNU_CONFIGURE= yes
@ -33,8 +31,22 @@ LIB_DEPENDS+= fribidi.0:${PORTSDIR}/converters/fribidi
CONFIGURE_ARGS+= --with-fribidi
.endif
.if !defined(WITH_MSN)
CONFIGURE_ARGS+= --disable-msn
.if defined(WITH_MSN)
CONFIGURE_ARGS+= --enable-msn
EXTRA_PATCHES= ${.CURDIR}/files/msn-*
pre-patch:
@${ECHO_CMD} "========================================================="
@${ECHO_CMD} "=====================Important !!!======================="
@${ECHO_CMD} "========================================================="
@${ECHO_CMD} "There may be some sticky legal issues with the new"
@${ECHO_CMD} "version of this protocol. Users should be aware that they"
@${ECHO_CMD} "might be in violation of the DMCA or other laws. If this"
@${ECHO_CMD} "is unacceptable, hit Ctrl-C now and remove WITH_MSN from"
@${ECHO_CMD} "your make flags. The FreeBSD group assumes no"
@${ECHO_CMD} "responsibility or liability for any losses or damages"
@${ECHO_CMD} "sustained by use or disuse of software in the ports tree."
@${ECHO_CMD} "========================================================="
@sleep 5
.endif
.if !defined(WITH_YAHOO)
@ -61,7 +73,7 @@ CONFIGURE_ARGS+= --disable-rss
CONFIGURE_ARGS+= --disable-lj
.endif
MAN1= centericq.1 cicqconv.1 cicqsync.1
MAN1= cicqconv.1 cicqsync.1
post-patch:
.for file in kkconsui-0.1/include/conf.h kkstrtext-0.1/conf.h kksystr-0.1/include/conf.h

View File

@ -1 +1 @@
MD5 (centericq-4.9.7.tar.gz) = 09c1672c0c2e5ef7e8a94052a71c58cc
MD5 (centericq-4.9.8.tar.gz) = 94e605d33f0dec7619bdfe6dad7b7a33

View File

@ -0,0 +1,32 @@
--- Makefile.in.orig Sat Oct 25 15:53:45 2003
+++ Makefile.in Mon Nov 3 20:14:01 2003
@@ -92,10 +92,10 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-SUBDIRS = firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 intl po contrib misc share src
+SUBDIRS = blip-0.1 firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 intl po contrib misc share src
# END OF MOTOR DIST TARGETS #
-EXTRA_DIST = centericq.1 centericq.motor config.rpath FAQ NEWS TODO README THANKS AUTHORS INSTALL ABOUT-NLS ChangeLog COPYING centericq.spec firetalk-0.1/* kkconsui-0.1/* kkstrtext-0.1/* libicq2000-0.1/* libjabber-0.1/* libyahoo2-0.1/* kksystr-0.1/* connwrap-0.1/*
+EXTRA_DIST = centericq.1 centericq.motor config.rpath FAQ NEWS TODO README THANKS AUTHORS INSTALL ABOUT-NLS ChangeLog COPYING centericq.spec blip-0.1/* firetalk-0.1/* kkconsui-0.1/* kkstrtext-0.1/* libicq2000-0.1/* libjabber-0.1/* libyahoo2-0.1/* kksystr-0.1/* connwrap-0.1/*
AUTOMAKE_OPTIONS = foreign
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
@@ -289,6 +289,7 @@
cd $(top_srcdir) \
&& $(AUTOMAKE) --include-deps --build-dir=$$here --srcdir-name=$(top_srcdir) --output-dir=$$top_distdir --foreign Makefile
$(mkinstalldirs) $(distdir)/connwrap-0.1 $(distdir)/firetalk-0.1 \
+ $(distdir)/blip-0.1 \
$(distdir)/kkconsui-0.1 $(distdir)/kkstrtext-0.1 \
$(distdir)/kksystr-0.1 $(distdir)/libicq2000-0.1 \
$(distdir)/libjabber-0.1 $(distdir)/libyahoo2-0.1
@@ -388,7 +389,7 @@
dist-hook:
cd $(top_distdir); subs=`egrep "^[:space:]*SUBDIRS" Makefile.am | sed 's/SUBDIRS[ =]\+//g'`; \
- echo "SUBDIRS = firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 $$subs" >>.makefile.am; \
+ echo "SUBDIRS = blip-0.1 firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 $$subs" >>.makefile.am; \
egrep -v "^[:space:]*SUBDIRS" Makefile.am >>.makefile.am; \
mv .makefile.am Makefile.am; autoconf && automake

View File

@ -0,0 +1,20 @@
--- src/hooks/abstracthook.cc.orig Sun Oct 19 06:57:26 2003
+++ src/hooks/abstracthook.cc Mon Nov 3 19:54:31 2003
@@ -31,6 +31,7 @@
#include "jabberhook.h"
#include "rsshook.h"
#include "ljhook.h"
+#include "msnhook.h"
#include "md5.h"
@@ -325,6 +326,9 @@
#endif
#ifdef BUILD_LJ
case livejournal: return lhook;
+#endif
+#ifdef BUILD_MSN
+ case msn: return mhook;
#endif
}

View File

@ -0,0 +1,12 @@
--- config.h.in.orig Thu Oct 16 06:07:45 2003
+++ config.h.in Mon Nov 3 21:31:23 2003
@@ -220,6 +220,9 @@
/* use gnutls */
#undef HAVE_GNUTLS
+/* build with msn support */
+#undef BUILD_MSN
+
/* build with yahoo support */
#undef BUILD_YAHOO

View File

@ -0,0 +1,72 @@
--- configure.orig Sat Oct 25 15:53:45 2003
+++ configure Mon Nov 3 20:21:06 2003
@@ -27,6 +27,8 @@
ac_help="$ac_help
--with-libgnutls-extra-prefix=PFX Prefix where libgnutls-extra is installed (optional)"
ac_help="$ac_help
+ --enable-msn Build with MSN!"
+ac_help="$ac_help
--disable-yahoo Build without Yahoo!"
ac_help="$ac_help
--disable-aim Build without AIM"
@@ -2365,6 +2367,14 @@
;;
esac
+# Check whether --enable-msn or --disable-msn was given.
+if test "${enable_msn+set}" = set; then
+ enableval="$enable_msn"
+ build_msn="$enableval"
+else
+ build_msn="yes"
+fi
+
# Check whether --enable-yahoo or --disable-yahoo was given.
if test "${enable_yahoo+set}" = set; then
enableval="$enable_yahoo"
@@ -2424,6 +2434,13 @@
+if test "x$build_msn" = xyes; then
+ BUILD_MSN_TRUE=
+ BUILD_MSN_FALSE='#'
+else
+ BUILD_MSN_TRUE='#'
+ BUILD_MSN_FALSE=
+fi
if test "x$build_yahoo" = xyes; then
BUILD_YAHOO_TRUE=
@@ -2478,6 +2495,13 @@
BUILD_LJ_FALSE=
fi
+if test "$build_msn" = "yes"; then
+ cat >> confdefs.h <<\EOF
+#define BUILD_MSN 1
+EOF
+
+fi
+
if test "$build_yahoo" = "yes"; then
cat >> confdefs.h <<\EOF
#define BUILD_YAHOO 1
@@ -4994,7 +5018,7 @@
-subdirs="firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1"
+subdirs="firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 blip-0.1"
trap '' 1 2 15
cat > confcache <<\EOF
@@ -5538,7 +5562,7 @@
esac
done
- for ac_config_dir in firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1; do
+ for ac_config_dir in firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 blip-0.1; do
# Do not complain, so a configure script can configure whichever
# parts of a large source tree are present.

View File

@ -0,0 +1,10 @@
--- src/imcontroller.cc.orig Thu Oct 16 07:40:18 2003
+++ src/imcontroller.cc Mon Nov 3 20:03:55 2003
@@ -31,6 +31,7 @@
#include "jabberhook.h"
#include "icqcontacts.h"
#include "eventmanager.h"
+#include "msnhook.h"
#define clr(c) conf.getcolor(c)

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,804 @@
--- src/hooks/msnhook.cc.orig Mon Nov 3 20:25:37 2003
+++ src/hooks/msnhook.cc Mon Nov 3 20:24:20 2003
@@ -0,0 +1,801 @@
+/*
+*
+* centericq MSN protocol handling class
+* $Id: msnhook.cc,v 1.67 2003/09/30 11:38:43 konst Exp $
+*
+* Copyright (C) 2001 by Konstantin Klyagin <konst@konst.org.ua>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or (at
+* your option) any later version.
+*
+* This program is distributed in the hope that it will be useful, but
+* WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+* General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+* USA
+*
+*/
+
+#include "icqcommon.h"
+
+#ifdef BUILD_MSN
+
+#include "msnhook.h"
+#include "icqconf.h"
+#include "icqface.h"
+#include "icqcontacts.h"
+#include "accountmanager.h"
+#include "eventmanager.h"
+#include "imlogger.h"
+#include "connwrap.h"
+
+#include "msn_bittybits.h"
+
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <netdb.h>
+#include <arpa/inet.h>
+
+msnhook mhook;
+
+static string nicknormalize(const string &nick) {
+ if(nick.find("@") == -1) return nick + "@hotmail.com";
+ return nick;
+}
+
+static string nicktodisp(const string &nick) {
+ int pos;
+ string r = nick;
+
+ if((pos = r.find("@")) != -1)
+ if(r.substr(pos+1) == "hotmail.com")
+ r.erase(pos);
+
+ return r;
+}
+
+struct st2imr {
+ char *name;
+ imstatus st;
+};
+
+const st2imr st2im[] = {
+ { "FLN", offline },
+ { "NLN", available },
+ { "HDN", invisible },
+ { "BSY", dontdisturb },
+ { "PHN", occupied },
+ { "AWY", away },
+ { "BRB", away },
+ { "LUN", notavail },
+ { "IDL", away },
+ { 0, offline }
+};
+
+static imstatus msn2imstatus(const string &sname) {
+ for(const st2imr *sa = st2im; sa->name; sa++)
+ if(sname == sa->name)
+ return sa->st;
+
+ return offline;
+}
+
+static const char *stat2name(imstatus st) {
+ for(const st2imr *sa = st2im; sa->name; sa++)
+ if(st == sa->st)
+ return sa->name;
+
+ return "NLN";
+}
+
+// ----------------------------------------------------------------------------
+
+msnhook::msnhook(): abstracthook(msn) {
+ ourstatus = offline;
+ fonline = false;
+
+ fcapabs.insert(hookcapab::synclist);
+ fcapabs.insert(hookcapab::changedetails);
+ fcapabs.insert(hookcapab::directadd);
+// fcapabs.insert(hookcapab::files);
+}
+
+msnhook::~msnhook() {
+}
+
+void msnhook::init() {
+ manualstatus = conf.getstatus(msn);
+}
+
+void msnhook::connect() {
+ icqconf::imaccount account = conf.getourid(msn);
+
+ face.log(_("+ [msn] connecting to the server"));
+
+ flogged = false;
+ fonline = true;
+
+ msn_init(&conn, nicknormalize(account.nickname).c_str(), account.password.c_str());
+ msn_connect(&conn, account.server.c_str(), account.port);
+
+ fonline = true;
+ flogged = true;
+}
+
+void msnhook::disconnect() {
+ msn_clean_up(&conn);
+}
+
+void msnhook::exectimers() {
+}
+
+void msnhook::main() {
+ vector<int>::const_iterator i;
+ fd_set rs, ws;
+ struct timeval tv;
+ int hsock;
+
+ FD_ZERO(&rs);
+ FD_ZERO(&ws);
+
+ tv.tv_sec = tv.tv_usec = 0;
+ hsock = 0;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i) {
+ FD_SET(*i, &rs);
+ hsock = max(hsock, *i);
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i) {
+ FD_SET(*i, &ws);
+ hsock = max(hsock, *i);
+ }
+
+ if(select(hsock+1, &rs, &ws, 0, &tv) > 0) {
+ for(i = rfds.begin(); i != rfds.end(); ++i)
+ if(FD_ISSET(*i, &rs)) {
+ msn_handle_incoming(*i, 1, 0);
+ return;
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i)
+ if(FD_ISSET(*i, &ws)) {
+ msn_handle_incoming(*i, 0, 1);
+ return;
+ }
+ }
+}
+
+void msnhook::getsockets(fd_set &rf, fd_set &wf, fd_set &efds, int &hsocket) const {
+ vector<int>::const_iterator i;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i) {
+ hsocket = max(hsocket, *i);
+ FD_SET(*i, &rf);
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i) {
+ hsocket = max(hsocket, *i);
+ FD_SET(*i, &wf);
+ }
+}
+
+bool msnhook::isoursocket(fd_set &rf, fd_set &wf, fd_set &efds) const {
+ vector<int>::const_iterator i;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i)
+ if(FD_ISSET(*i, &rf))
+ return true;
+
+ for(i = wfds.begin(); i != wfds.end(); ++i)
+ if(FD_ISSET(*i, &wf))
+ return true;
+
+ return false;
+}
+
+bool msnhook::online() const {
+ return fonline;
+}
+
+bool msnhook::logged() const {
+ return fonline && flogged;
+}
+
+bool msnhook::isconnecting() const {
+ return fonline && !flogged;
+}
+
+bool msnhook::enabled() const {
+ return true;
+}
+
+bool msnhook::send(const imevent &ev) {
+ string text;
+
+ if(ev.gettype() == imevent::message) {
+ const immessage *m = static_cast<const immessage *>(&ev);
+ if(m) text = m->gettext();
+
+ } else if(ev.gettype() == imevent::url) {
+ const imurl *m = static_cast<const imurl *>(&ev);
+ if(m) text = m->geturl() + "\n\n" + m->getdescription();
+
+ } else if(ev.gettype() == imevent::file) {
+ const imfile *m = static_cast<const imfile *>(&ev);
+ vector<imfile::record> files = m->getfiles();
+ vector<imfile::record>::const_iterator ir;
+
+ for(ir = files.begin(); ir != files.end(); ++ir) {
+ imfile::record r;
+ invitation_ftp *p;
+
+ r.fname = ir->fname;
+ r.size = ir->size;
+
+ imfile fr(ev.getcontact(), imevent::outgoing, "", vector<imfile::record>(1, r));
+
+ if(p = msn_filetrans_send(&conn, ir->fname.c_str()))
+ transferinfo[fr].first = p;
+ }
+
+ return true;
+ }
+
+ icqcontact *c = clist.get(ev.getcontact());
+ text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf-8");
+
+ if(c)
+ if(c->getstatus() != offline || !c->inlist()) {
+ msn_send_IM(&conn, nicknormalize(ev.getcontact().nickname).c_str(), text.c_str());
+ return true;
+ }
+
+ return false;
+}
+
+void msnhook::sendnewuser(const imcontact &ic) {
+ if(logged()) {
+ icqcontact *c;
+ imcontact icc(nicktodisp(ic.nickname), msn);
+
+ if(icc.nickname != ic.nickname)
+ if(c = clist.get(ic)) {
+ c->setdesc(icc);
+ c->setnick(icc.nickname);
+ c->setdispnick(icc.nickname);
+ }
+
+ msn_add_to_list(&conn, "FL", nicknormalize(ic.nickname).c_str());
+ }
+
+ requestinfo(ic);
+}
+
+void msnhook::setautostatus(imstatus st) {
+ if(st != offline) {
+ if(getstatus() == offline) {
+ connect();
+ } else {
+ logger.putourstatus(msn, ourstatus, st);
+ msn_set_state(&conn, stat2name(ourstatus = st));
+ }
+ } else {
+ if(getstatus() != offline) {
+ disconnect();
+ }
+ }
+}
+
+imstatus msnhook::getstatus() const {
+ return online() ? ourstatus : offline;
+}
+
+void msnhook::removeuser(const imcontact &ic) {
+ removeuser(ic, true);
+}
+
+void msnhook::removeuser(const imcontact &ic, bool report) {
+ if(online()) {
+ if(report)
+ face.log(_("+ [msn] removing %s from the contacts"), ic.nickname.c_str());
+
+ msn_del_from_list(&conn, "FL", nicknormalize(ic.nickname).c_str());
+ }
+}
+
+void msnhook::requestinfo(const imcontact &ic) {
+ icqcontact *c = clist.get(ic);
+
+ if(!c) {
+ c = clist.get(contactroot);
+ c->clear();
+ }
+
+ icqcontact::moreinfo m = c->getmoreinfo();
+ icqcontact::basicinfo b = c->getbasicinfo();
+
+ b.email = nicknormalize(ic.nickname);
+ m.homepage = "http://members.msn.com/" + b.email;
+
+ if(ic.nickname == conf.getourid(msn).nickname)
+ c->setnick(friendlynicks[ic.nickname]);
+
+ c->setmoreinfo(m);
+ c->setbasicinfo(b);
+}
+
+void msnhook::lookup(const imsearchparams &params, verticalmenu &dest) {
+ if(params.reverse) {
+ vector<pair<string, string> >::const_iterator i = slst["RL"].begin();
+
+ while(i != slst["RL"].end()) {
+ icqcontact *c = new icqcontact(imcontact(nicktodisp(i->first), msn));
+ c->setnick(i->second);
+
+ dest.additem(conf.getcolor(cp_clist_msn), c, (string) " " + i->first);
+ ++i;
+ }
+ face.findready();
+
+ face.log(_("+ [msn] reverse users listing finished, %d found"),
+ slst["RL"].size());
+
+ dest.redraw();
+ }
+}
+
+vector<icqcontact *> msnhook::getneedsync() {
+ int i;
+ vector<icqcontact *> r;
+ bool found;
+
+ for(i = 0; i < clist.count; i++) {
+ icqcontact *c = (icqcontact *) clist.at(i);
+
+ if(c->getdesc().pname == msn) {
+ vector<pair<string, string> >::const_iterator fi = slst["FL"].begin();
+
+ for(found = false; fi != slst["FL"].end() && !found; ++fi)
+ found = c->getdesc().nickname == fi->first;
+
+ if(!found)
+ r.push_back(c);
+ }
+ }
+
+ return r;
+}
+
+void msnhook::sendupdateuserinfo(const icqcontact &c) {
+ msn_set_friendlyname(&conn, c.getnick().c_str());
+}
+
+void msnhook::checkfriendly(icqcontact *c, const string friendlynick, bool forcefetch) {
+ string oldnick = c->getnick();
+ string newnick = siconv(unmime(friendlynick), "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+
+ c->setnick(newnick);
+
+ if(forcefetch || (oldnick != newnick && c->getdispnick() != oldnick) || oldnick.empty()) {
+ c->setdispnick(newnick);
+ face.relaxedupdate();
+ }
+}
+
+void msnhook::checkinlist(imcontact ic) {
+ icqcontact *c = clist.get(ic);
+ vector<icqcontact *> notremote = getneedsync();
+
+ if(c)
+ if(c->inlist())
+ if(find(notremote.begin(), notremote.end(), c) != notremote.end())
+ mhook.sendnewuser(ic);
+}
+
+bool msnhook::knowntransfer(const imfile &fr) const {
+ return transferinfo.find(fr) != transferinfo.end();
+}
+
+void msnhook::replytransfer(const imfile &fr, bool accept, const string &localpath) {
+ if(accept) {
+ transferinfo[fr].second = localpath;
+
+ if(transferinfo[fr].second.substr(transferinfo[fr].second.size()-1) != "/")
+ transferinfo[fr].second += "/";
+
+ transferinfo[fr].second += justfname(fr.getfiles().begin()->fname);
+ msn_filetrans_accept(transferinfo[fr].first, transferinfo[fr].second.c_str());
+
+ } else {
+ msn_filetrans_reject(transferinfo[fr].first);
+ transferinfo.erase(fr);
+
+ }
+}
+
+void msnhook::aborttransfer(const imfile &fr) {
+ msn_filetrans_reject(transferinfo[fr].first);
+
+ face.transferupdate(fr.getfiles().begin()->fname, fr,
+ icqface::tsCancel, 0, 0);
+
+ transferinfo.erase(fr);
+}
+
+bool msnhook::getfevent(invitation_ftp *fhandle, imfile &fr) {
+ map<imfile, pair<invitation_ftp *, string> >::const_iterator i = transferinfo.begin();
+
+ while(i != transferinfo.end()) {
+ if(i->second.first == fhandle) {
+ fr = i->first;
+ return true;
+ }
+ ++i;
+ }
+
+ return false;
+}
+
+// ----------------------------------------------------------------------------
+
+static void log(const string &s) {
+#ifdef DEBUG
+ face.log(s);
+#endif
+}
+
+int ext_debug( char *str )
+{
+ log( str );
+ return 0;
+}
+
+void ext_register_sock(int s, int reading, int writing) {
+ log("ext_register_sock");
+ if(reading) mhook.rfds.push_back(s);
+ if(writing) mhook.wfds.push_back(s);
+}
+
+void ext_unregister_sock(int s) {
+ log("ext_unregister_sock");
+ vector<int>::iterator i;
+
+ i = find(mhook.rfds.begin(), mhook.rfds.end(), s);
+ if(i != mhook.rfds.end()) mhook.rfds.erase(i);
+
+ i = find(mhook.wfds.begin(), mhook.wfds.end(), s);
+ if(i != mhook.wfds.end()) mhook.wfds.erase(i);
+}
+
+void ext_got_friendlyname(msnconn * conn, const char * friendlyname) {
+ log("ext_got_friendlyname");
+
+ if(friendlyname)
+ if(strlen(friendlyname))
+ mhook.friendlynicks[conf.getourid(msn).nickname] = friendlyname;
+}
+
+void ext_got_info(msnconn *conn, syncinfo *info) {
+ log("ext_got_info");
+
+ userdata *ud;
+ llist *lst, *pl;
+ imcontact ic;
+
+ for(lst = info->fl; lst; lst = lst->next) {
+ ud = (userdata *) lst->data;
+
+ mhook.slst["FL"].push_back(make_pair(ud->username, ud->friendlyname));
+
+ ic = imcontact(nicktodisp(ud->username), msn);
+ icqcontact *c = clist.get(ic);
+ if(!c) c = clist.addnew(ic, false);
+
+ icqcontact::basicinfo bi = c->getbasicinfo();
+ icqcontact::workinfo wi = c->getworkinfo();
+
+ for(pl = ud->phone; pl; pl = pl->next) {
+ phonedata *pd = (phonedata *) pl->data;
+ string title = pd->title ? pd->title : "";
+
+ if(pd->number)
+ if(strlen(pd->number)) {
+ if(title == "PHH") bi.phone = pd->number; else
+ if(title == "PHW") wi.phone = pd->number; else
+ if(title == "PHM") bi.cellular = pd->number;
+ }
+ }
+
+ c->setbasicinfo(bi);
+ c->setworkinfo(wi);
+ }
+
+ for(lst = info->rl; lst; lst = lst->next) {
+ ud = (userdata *) lst->data;
+ mhook.slst["RL"].push_back(make_pair(ud->username, ud->friendlyname));
+ }
+
+ mhook.setautostatus(mhook.ourstatus);
+}
+
+void ext_latest_serial(msnconn * conn, int serial) {
+ log("ext_latest_serial");
+}
+
+void ext_got_GTC(msnconn * conn, char c) {
+ log("ext_got_GTC");
+}
+
+void ext_got_BLP(msnconn * conn, char c) {
+ log("ext_got_BLP");
+}
+
+void ext_new_RL_entry(msnconn *conn, const char *username, const char *friendlyname) {
+ log("ext_new_RL_entry");
+ msn_add_to_list(&mhook.conn, "AL", username);
+
+ imcontact ic(nicktodisp(username), msn);
+ mhook.checkinlist(ic);
+ em.store(imnotification(ic, _("The user has added you to his/her contact list")));
+}
+
+void ext_new_list_entry(msnconn *conn, const char *lst, const char *username) {
+ log("ext_new_list_entry");
+ mhook.slst[lst].push_back(make_pair(username, string()));
+}
+
+void ext_del_list_entry(msnconn *conn, const char *lst, const char *username) {
+ log("ext_del_list_entry");
+
+ vector<pair<string, string> >::iterator i = mhook.slst[lst].begin();
+ while(i != mhook.slst[lst].end()) {
+ if(i->first == username) {
+ mhook.slst[lst].erase(i);
+ i = mhook.slst[lst].begin();
+ } else {
+ ++i;
+ }
+ }
+}
+
+void ext_show_error(msnconn * conn, const char * msg) {
+ log("ext_show_error");
+ log(msg);
+}
+
+void ext_buddy_set(msnconn * conn, const char * buddy, const char * friendlyname, const char * status) {
+ log("ext_buddy_set");
+ imcontact ic(nicktodisp(buddy), msn);
+ icqcontact *c = clist.get(ic);
+ bool forcefetch;
+
+ if(forcefetch = !c)
+ c = clist.addnew(ic, false);
+
+ if(friendlyname)
+ mhook.checkfriendly(c, friendlyname, forcefetch);
+
+ logger.putonline(ic, c->getstatus(), msn2imstatus(status));
+ c->setstatus(msn2imstatus(status));
+}
+
+void ext_buddy_offline(msnconn * conn, const char * buddy) {
+ log("ext_buddy_offline");
+ ext_buddy_set(conn, buddy, 0, "FLN");
+}
+
+void ext_got_SB(msnconn * conn, void * tag) {
+ log("ext_got_SB");
+}
+
+void ext_user_joined(msnconn *conn, const char *username, const char *friendlyname, int is_initial) {
+ log("ext_user_joined");
+}
+
+void ext_user_left(msnconn *conn, const char *username) {
+ log("ext_user_left");
+}
+
+void ext_got_IM(msnconn *conn, const char *username, const char *friendlyname, message *msg) {
+ log("ext_got_IM");
+ imcontact ic(nicktodisp(username), msn);
+
+ mhook.checkinlist(ic);
+
+ string text = siconv(msg->body, "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+ em.store(immessage(ic, imevent::incoming, text));
+}
+
+void ext_IM_failed(msnconn *conn) {
+ log("ext_IM_failed");
+}
+
+void ext_typing_user(msnconn *conn, const char *username, const char *friendlyname) {
+ log("ext_typing_user");
+ icqcontact *c = clist.get(imcontact(nicktodisp(username), msn));
+ if(c) c->setlasttyping(timer_current);
+}
+
+void ext_initial_email(msnconn *conn, int unread_inbox, int unread_folders) {
+ log("ext_initial_email");
+
+ face.log(_("+ [msn] unread e-mail: %d in inbox, %d in folders"),
+ unread_inbox, unread_folders);
+}
+
+void ext_new_mail_arrived(msnconn *conn, const char *from, const char *subject) {
+ log("ext_new_mail_arrived");
+
+ face.log(_("+ [msn] e-mail from %s, %s"), from, subject);
+ clist.get(contactroot)->playsound(imevent::email);
+}
+
+void ext_filetrans_invite(msnconn *conn, const char *username, const char *friendlyname, invitation_ftp *inv) {
+ log("ext_filetrans_invite");
+
+ if(!mhook.fcapabs.count(hookcapab::files))
+ return;
+
+ imfile::record r;
+ r.fname = inv->filename;
+ r.size = inv->filesize;
+
+ imcontact ic(nicktodisp(username), msn);
+ mhook.checkinlist(ic);
+
+ imfile fr(ic, imevent::incoming, "", vector<imfile::record>(1, r));
+
+ mhook.transferinfo[fr].first = inv;
+ em.store(fr);
+
+ face.transferupdate(inv->filename, fr, icqface::tsInit, inv->filesize, 0);
+}
+
+void ext_filetrans_progress(invitation_ftp *inv, const char *status, unsigned long sent, unsigned long total) {
+ log("ext_filetrans_progress");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr,
+ icqface::tsProgress, total, sent);
+ }
+}
+
+void ext_filetrans_failed(invitation_ftp *inv, int error, const char *message) {
+ log("ext_filetrans_failed");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr, icqface::tsError, 0, 0);
+ mhook.transferinfo.erase(fr);
+ }
+}
+
+void ext_filetrans_success(invitation_ftp *inv) {
+ log("ext_filetrans_success");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr, icqface::tsFinish, 0, 0);
+ mhook.transferinfo.erase(fr);
+ }
+}
+
+void ext_new_connection(msnconn *conn) {
+ log("ext_new_connection");
+ if(conn->type == CONN_NS) {
+ msn_sync_lists(conn, 0);
+ logger.putourstatus(msn, offline, mhook.ourstatus = mhook.manualstatus);
+ mhook.flogged = true;
+ face.log(_("+ [msn] logged in"));
+ face.update();
+ }
+}
+
+void ext_closing_connection(msnconn *conn) {
+ log("ext_closing_connection");
+ if(conn->type == CONN_NS) {
+ mhook.rfds.clear();
+ mhook.wfds.clear();
+ logger.putourstatus(msn, mhook.getstatus(), mhook.ourstatus = offline);
+ clist.setoffline(msn);
+ mhook.fonline = false;
+ mhook.slst.clear();
+ face.log(_("+ [msn] disconnected"));
+ face.update();
+ }
+}
+
+void ext_changed_state(msnconn *conn, const char *state) {
+ log("ext_changed_state");
+}
+
+int ext_do_connect_socket(const char *hostname, int port, int ssl) {
+ struct sockaddr_in sa;
+ struct hostent *hp;
+ int a, s;
+ string msgerr = _("+ [msn] cannot connect: ");
+
+ hp = gethostbyname(hostname);
+ if(!hp) {
+ face.log(msgerr + _("could not resolve hostname"));
+ errno = ECONNREFUSED;
+ return -1;
+ }
+
+ memset(&sa, 0, sizeof(sa));
+ memcpy((char *) &sa.sin_addr, hp->h_addr, hp->h_length);
+ sa.sin_family = hp->h_addrtype;
+ sa.sin_port = htons((u_short) port);
+
+ if((s = socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0)
+ return -1;
+
+ if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), ssl) < 0) {
+ face.log(msgerr + _("verify the hostname and port"));
+ close(s);
+ return -1;
+ }
+
+ return s;
+}
+
+int ext_connect_socket_ssl(const char *hostname, int port) {
+ log("ext_connect_socket_ssl");
+ return ext_do_connect_socket(hostname, port, 1);
+}
+
+int ext_connect_socket(const char *hostname, int port) {
+ log("ext_connect_socket");
+ return ext_do_connect_socket(hostname, port, 0);
+}
+
+int ext_server_socket(int port) {
+ log("ext_server_socket");
+ int s;
+ struct sockaddr_in addr;
+
+ if((s = socket(AF_INET, SOCK_STREAM, 0)) < 0)
+ return -1;
+
+ memset(&addr, 0, sizeof(addr));
+ addr.sin_family = AF_INET;
+ addr.sin_port = htons(port);
+
+ if(bind(s, (sockaddr *) &addr, sizeof(addr)) < 0 || listen(s, 1) < 0) {
+ close(s);
+ return -1;
+ }
+
+ return s;
+}
+
+char *ext_get_IP() {
+ log("ext_get_IP");
+ struct hostent *hn;
+ char buf2[1024];
+
+ gethostname(buf2, 1024);
+ hn = gethostbyname(buf2);
+
+ return inet_ntoa(*((struct in_addr*) hn->h_addr));
+}
+
+void ext_protocol_log(const char *buf, int readev, int writeev) {
+ if(readev) {
+ log(string("[IN] ") + buf);
+ } else if(writeev) {
+ log(string("[OUT] ") + buf);
+ }
+}
+
+#endif

View File

@ -0,0 +1,92 @@
--- src/hooks/msnhook.h.orig Mon Nov 3 20:25:39 2003
+++ src/hooks/msnhook.h Mon Nov 3 20:24:23 2003
@@ -0,0 +1,89 @@
+#ifndef __MSNHOOK_H__
+#define __MSNHOOK_H__
+
+#include "abstracthook.h"
+
+#ifdef BUILD_MSN
+
+#include "msn_core.h"
+
+class msnhook : public abstracthook {
+
+ friend void ext_register_sock(int s, int reading, int writing);
+ friend void ext_unregister_sock(int s);
+ friend void ext_new_connection(msnconn *conn);
+ friend void ext_closing_connection(msnconn * conn);
+ friend void ext_buddy_set(msnconn *conn, const char *buddy, const char *friendlyname, const char *status);
+ friend void ext_got_info(msnconn *conn, syncinfo *info);
+ friend void ext_got_friendlyname(msnconn *conn, const char *friendlyname);
+ friend void ext_new_RL_entry(msnconn *conn, const char *username, const char *friendlyname);
+ friend void ext_new_list_entry(msnconn *conn, const char *lst, const char *username);
+ friend void ext_del_list_entry(msnconn *conn, const char *lst, const char *username);
+ friend void ext_got_IM(msnconn *conn, const char *username, const char *friendlyname, message *msg);
+ friend void ext_filetrans_invite(msnconn *conn, const char *username, const char *friendlyname, invitation_ftp *inv);
+ friend void ext_typing_user(msnconn *conn, const char *username, const char *friendlyname);
+ friend void ext_filetrans_progress(invitation_ftp *inv, const char *status, unsigned long sent, unsigned long total);
+ friend void ext_filetrans_failed(invitation_ftp *inv, int error, const char *message);
+ friend void ext_filetrans_success(invitation_ftp *inv);
+
+ protected:
+ imstatus ourstatus;
+ bool fonline, flogged;
+ msnconn conn;
+
+ vector<int> rfds, wfds;
+ map<string, string> friendlynicks;
+ map<string, vector<pair<string, string> > > slst;
+ map<imfile, pair<invitation_ftp *, string> > transferinfo;
+
+ void checkfriendly(icqcontact *c, const string friendlynick,
+ bool forcefetch = false);
+
+ void checkinlist(imcontact ic);
+
+ void removeuser(const imcontact &ic, bool report);
+ bool getfevent(invitation_ftp *fhandle, imfile &fr);
+
+ public:
+ msnhook();
+ ~msnhook();
+
+ void init();
+
+ void connect();
+ void disconnect();
+ void exectimers();
+ void main();
+
+ void getsockets(fd_set &rf, fd_set &wf, fd_set &ef, int &hsocket) const;
+ bool isoursocket(fd_set &rf, fd_set &wf, fd_set &ef) const;
+
+ bool online() const;
+ bool logged() const;
+ bool isconnecting() const;
+ bool enabled() const;
+
+ bool send(const imevent &ev);
+
+ void sendnewuser(const imcontact &c);
+ void removeuser(const imcontact &ic);
+ void requestinfo(const imcontact &ic);
+
+ void sendupdateuserinfo(const icqcontact &c);
+
+ void setautostatus(imstatus st);
+ imstatus getstatus() const;
+
+ void lookup(const imsearchparams &params, verticalmenu &dest);
+ vector<icqcontact *> getneedsync();
+
+ bool knowntransfer(const imfile &fr) const;
+ void replytransfer(const imfile &fr, bool accept, const string &localpath = string());
+ void aborttransfer(const imfile &fr);
+};
+
+extern msnhook mhook;
+
+#endif
+
+#endif

View File

@ -0,0 +1,17 @@
--- src/Makefile.in.orig Sat Oct 25 15:53:46 2003
+++ src/Makefile.in Mon Nov 3 20:16:35 2003
@@ -92,11 +92,11 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl
+INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl -I$(top_srcdir)/blip-0.1
bin_PROGRAMS = centericq
centericq_SOURCES = centericq.cc icqcontact.cc icqgroups.cc eventmanager.cc icqdialogs.cc icqhist.cc imexternal.cc imcontact.cc imlogger.cc accountmanager.cc icqcontacts.cc icqmlist.cc imcontroller.cc icqconf.cc imevents.cc icqface.cc centermain.cc icqgroup.cc
-centericq_LDFLAGS = -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1
-centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@
+centericq_LDFLAGS = -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1 -L$(top_srcdir)/blip-0.1
+centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@ -intl -lblip
SUBDIRS = hooks
EXTRA_DIST = centericq.cc icqcontact.cc icqgroups.cc eventmanager.cc icqdialogs.cc icqhist.cc imexternal.cc imcontact.cc imlogger.cc accountmanager.cc icqcontacts.cc icqmlist.cc imcontroller.cc icqconf.cc imevents.cc icqface.cc centermain.cc icqgroup.cc icqmlist.h imcontroller.h icqcommon.h icqcontacts.h centericq.h icqgroup.h imcontact.h accountmanager.h eventmanager.h imevents.h icqcontact.h imlogger.h icqconf.h icqface.h icqgroups.h icqhist.h imexternal.h
AUTOMAKE_OPTIONS = foreign

View File

@ -0,0 +1,34 @@
--- src/hooks/Makefile.in.orig Sat Oct 25 15:53:46 2003
+++ src/hooks/Makefile.in Mon Nov 3 21:35:39 2003
@@ -92,10 +92,10 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl
+INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl -I$(top_srcdir)/blip-0.1
noinst_LIBRARIES = libhooks.a
-libhooks_a_SOURCES = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc
-EXTRA_DIST = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc yahoohook.h aimhook.h jabberhook.h icqhook.h irchook.h abstracthook.h rsshook.h HTTPClient.h ljhook.h
+libhooks_a_SOURCES = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc msnhook.cc
+EXTRA_DIST = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc msnhook.cc yahoohook.h aimhook.h jabberhook.h icqhook.h irchook.h abstracthook.h rsshook.h HTTPClient.h ljhook.h msnhook.h
mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
CONFIG_HEADER = ../../config.h
CONFIG_CLEAN_FILES =
@@ -108,7 +108,7 @@
LIBS = @LIBS@
libhooks_a_LIBADD =
libhooks_a_OBJECTS = yahoohook.o jabberhook.o aimhook.o icqhook.o \
-irchook.o abstracthook.o rsshook.o HTTPClient.o ljhook.o
+irchook.o abstracthook.o rsshook.o HTTPClient.o ljhook.o msnhook.o
AR = ar
CXXFLAGS = @CXXFLAGS@
CXXCOMPILE = $(CXX) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS)
@@ -123,7 +123,7 @@
GZIP_ENV = --best
DEP_FILES = .deps/HTTPClient.P .deps/abstracthook.P .deps/aimhook.P \
.deps/icqhook.P .deps/irchook.P .deps/jabberhook.P .deps/ljhook.P \
-.deps/rsshook.P .deps/yahoohook.P
+.deps/rsshook.P .deps/yahoohook.P .deps/msnhook.P
SOURCES = $(libhooks_a_SOURCES)
OBJECTS = $(libhooks_a_OBJECTS)

View File

@ -1,11 +0,0 @@
--- src/icqconf.cc.orig Wed Oct 1 08:27:45 2003
+++ src/icqconf.cc Wed Oct 8 17:28:21 2003
@@ -270,7 +270,7 @@
if(getantispam()) f << "antispam" << endl;
if(getmailcheck()) f << "mailcheck" << endl;
if(getaskaway()) f << "askaway" << endl;
- f << "defcharset" << getdefcharset() << endl;
+ f << "defcharset\t" << getdefcharset() << endl;
param = "";
for(protocolname pname = icq; pname != protocolname_size; (int) pname += 1)

View File

@ -1,28 +0,0 @@
--- blip-0.1/msn_bittybits.C.orig Mon Dec 9 20:31:41 2002
+++ blip-0.1/msn_bittybits.C Thu Oct 23 20:02:19 2003
@@ -18,6 +18,8 @@
char c;
int pos=0, numspaces=0;
+ *numargs = 0;
+
while(1)
{
if(read(sock, &c, 1)<1)
@@ -259,13 +261,16 @@
{
if(*rptr=='\0')
{ *wptr='\0'; break; }
+
if(!(isalpha(*rptr) || isdigit(*rptr)))
{
+ if ( *rptr != '\xc2' && *rptr != '\xb0' ) {
sprintf(wptr, "%%%2x", (int)(*rptr));
rptr++;
wptr+=3;
continue;
+ }
}
*wptr=*rptr;

View File

@ -1,923 +0,0 @@
--- blip-0.1/msn_core.C.orig Sat Dec 14 07:58:01 2002
+++ blip-0.1/msn_core.C Thu Oct 23 20:02:19 2003
@@ -18,19 +18,18 @@
#include <sys/stat.h>
#include "md5.h"
-
#include "msn_core.h"
#include "msn_bittybits.h"
#include "msn_interface.h"
+#include "../connwrap-0.1/connwrap.h"
#define DEBUG 1
+#define MSN_VERSION_ID 0 // ID that is sent after commands like CHG, NLN, etc.
// Define all those extern'ed variables in msn_core.h:
llist * connections=NULL;
-
int next_trid=10;
char buf[BUF_SIZE]; // used for anything temporary
-
char * errors[1000];
char default_error_msg[]="Unknown error code";
@@ -218,143 +217,151 @@
write(conn->sock, buf, strlen(buf));
}
-void msn_sync_lists(msnconn * conn, int version)
+void msn_get_list_info( msnconn *conn, int nargs, char **args )
{
- syncinfo * info=new syncinfo;
+ char buf[ 1000 ];
+ syncinfo *info;
- info->serial=version;
+ info = conn->sync_info;
- sprintf(buf, "SYN %d %d\r\n", next_trid, version);
- write(conn->sock, buf, strlen(buf));
+ if ( NULL == info )
+ {
+ ext_debug("error! : conn->sync_info == NULL in msn_get_list_info");
+ return ;
+ }
- msn_add_callback(conn, msn_syncdata, next_trid, info);
- next_trid++;
-}
+ if ( !nargs )
+ return ;
-void msn_syncdata(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- syncinfo * info=(syncinfo *)data;
-
- if(!strcmp(args[0], "SYN"))
+ if ( !strcmp( args[ 0 ], "SYN" ) )
{
- if(info->serial==atoi(args[2]))
+ if ( info->serial == atoi( args[ 2 ] ) )
{
delete info;
- info=NULL;
- msn_del_callback(conn, trid);
+ info = NULL;
ext_got_info(conn, NULL);
return;
- } else {
- info->serial=atoi(args[2]);
- ext_latest_serial(conn, info->serial);
- msn_add_callback(conn, msn_phonedata, info->serial, info);
}
+
+ info->serial = atoi( args[ 2 ] );
+ ext_latest_serial( conn, info->serial );
+ info->nContacts = atoi( args[ 3 ] );
+ info->nGroups = atoi( args[ 4 ] );
+ return ;
}
- if(!strcmp(args[0], "LST"))
- {
- if(!strcmp(args[2], "FL"))
- {
- if(!strcmp(args[5], "0"))
+ if ( !strcmp( args[ 0 ], "GTC" ) )
{
- info->fl=NULL; info->complete|=LST_FL;
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->fl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_FL; }
- }
+ info->gtc = args[ 1 ][ 0 ];
+ info->complete |= COMPLETE_GTC;
+ ext_got_GTC( conn, args[ 1 ][ 0 ] );
}
- if(!strcmp(args[2], "RL"))
- {
- if(!strcmp(args[5], "0"))
+
+ if ( !strcmp( args[ 0 ], "BLP" ) )
{
- info->rl=NULL; info->complete|=LST_RL; // no mates! :-)
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->rl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_RL; }
+ info->blp = args[ 1 ][0];
+ info->complete |= COMPLETE_BLP;
+ ext_got_BLP( conn, args[ 1 ][ 0 ] );
}
+
+ if ( !strcmp( args[ 0 ], "PRP" ) )
+ {
+ // We just eat PRP-codes.
+ return ;
}
- if(!strcmp(args[2], "AL"))
+
+ if ( !strcmp( args[ 0 ], "LSG" ) )
{
- if(!strcmp(args[5], "0"))
+ if ( !info->nContacts )
{
- info->al=NULL; info->complete|=LST_AL;
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->al, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_AL; }
+ msn_check_rl(conn, info);
+ ext_got_info(conn, info);
+ delete info;
+ conn->sync = 0;
}
+
+ // Just eat 'm.
+ return ;
}
- if(!strcmp(args[2], "BL"))
- {
- if(!strcmp(args[5], "0"))
+
+ if ( !strcmp( args[ 0 ], "BPR" ) )
{
- info->bl=NULL; info->complete|=LST_BL;
+ if ( !info->nFound ) {
+ ext_debug("MSNp8: error: got BPR without contact");
} else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->bl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_BL; }
+ llist *ll = info->fl;
+
+ while( ll ) {
+ userdata * ud = (userdata *) ll->data;
+
+ if( !strcmp( ud->username, info->last_user_handled ) )
+ {
+ phonedata * newphone=new phonedata();
+ newphone->title=msn_permstring(args[1]);
+ newphone->number=msn_decode_URL(msn_permstring(args[2]));
+ msn_add_to_llist( ud->phone, newphone );
+ break;
}
+
+ ll = ll->next;
}
}
- if(!strcmp(args[0], "GTC"))
- {
- info->gtc=args[3][0];
- info->complete|=COMPLETE_GTC;
- ext_got_GTC(conn, args[3][0]);
+ return ;
}
- if(!strcmp(args[0], "BLP"))
+ // 0 1 2
+ // LST email@address.com Friendly%20Nickname w x,y,z
+ if ( !strcmp( args[ 0 ], "LST" ) )
{
- info->blp=args[3][0];
- info->complete|=COMPLETE_BLP;
- ext_got_BLP(conn, args[3][0]);
- }
+ // XXX - Todo: see if the user is really on our FL
+ // list and handle the BL list.
+
+ userdata *newuser_fl = new userdata();
+ newuser_fl->username = msn_permstring( args[ 1 ] );
+ newuser_fl->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ info->last_user_handled = newuser_fl->username;
+
+ msn_add_to_llist( info->fl, newuser_fl );
+
+ userdata *newuser_rl = new userdata();
+ newuser_rl->username = msn_permstring( args[ 1 ] );
+ newuser_rl->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ msn_add_to_llist( info->rl, newuser_rl );
- if(info->complete == (LST_FL|LST_RL|LST_AL|LST_BL|COMPLETE_BLP|COMPLETE_GTC))
+ userdata *newuser_al = new userdata();
+ newuser_al->username = msn_permstring( args[ 1 ] );
+ newuser_al->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ msn_add_to_llist( info->al, newuser_al );
+
+ info->nFound++;
+
+ if ( info->nFound == info->nContacts )
{
- msn_del_callback(conn, trid);
- msn_del_callback(conn, info->serial);
msn_check_rl(conn, info);
ext_got_info(conn, info);
delete info;
+ conn->sync = 0;
+ }
}
}
-void msn_phonedata(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
+void msn_sync_lists(msnconn * conn, int version)
{
- syncinfo * info=(syncinfo *)data;
+ syncinfo * info=new syncinfo;
- if(!strcmp(args[0], "BPR"))
- {
- llist * ll = info->fl;
- while(ll) {
- userdata * ud = (userdata *) ll->data;
- if(!strcmp(ud->username, args[2]))
- {
- phonedata * newphone=new phonedata();
- newphone->title=msn_permstring(args[3]);
- newphone->number=msn_decode_URL(msn_permstring(args[4]));
- msn_add_to_llist(ud->phone, newphone);
- break;
- }
- ll = ll->next;
- }
- }
+ info->serial=version;
+
+ sprintf(buf, "SYN %d %d\r\n", next_trid, version);
+ write(conn->sock, buf, strlen(buf));
+
+ conn->sync = 1;
+ conn->sync_info = info;
+
+ next_trid++;
}
void msn_check_rl(msnconn * conn, syncinfo * info)
@@ -544,6 +551,11 @@
if(!readable) { return; }
args=msn_read_line(sock, &numargs);
+ if ( !numargs )
+ {
+ ext_debug("msn: error: no arguments for this data");
+ return ;
+ }
if(args==NULL)
{
@@ -582,6 +594,22 @@
trid=atoi(args[1]);
+ if ( conn->sync )
+ {
+ // connection is synching. is this a SYNC-relation instruction?
+ if ( !strcmp( args[ 0 ], "SYN" ) || !strcmp( args[ 0 ], "GTC") || !strcmp( args[ 0 ], "BLP" ) ||
+ !strcmp( args[ 0 ], "PRP" ) || !strcmp( args[ 0 ], "LSG") || !strcmp( args[ 0 ], "BPR" ) ||
+ !strcmp( args[ 0 ], "LST" ) )
+ {
+ msn_get_list_info( conn, numargs, args );
+ delete args[0];
+ delete args;
+ return ;
+ }
+
+ // else: it's a normal message
+ }
+
list=conn->callbacks;
if(list!=NULL && trid>0)
@@ -775,6 +803,10 @@
#endif
if((tmp=strstr(content, "; charset"))!=NULL) { *tmp='\0'; }
+ if(!strcmp(content, "text/x-msmsgsprofile"))
+ {
+ ext_debug("MSNp8: got x-msmsgsprofile");
+ } else
if(!strcmp(content, "text/plain"))
{
message * msg=new message;
@@ -1024,7 +1056,6 @@
write(conn->sock, "VER MSNFTP\r\n", strlen("VER MSNFTP\r\n"));
}
-
void msn_handle_filetrans_incoming(msnconn * conn, int readable, int writable)
{
authdata_FTP * auth=(authdata_FTP *)conn->auth;
@@ -1445,10 +1476,12 @@
md5_init(&state);
md5_append(&state, (md5_byte_t *)(args[2]), strlen(args[2]));
- md5_append(&state, (md5_byte_t *)"Q1P7W2E4J9R8U3S5", 16);
+ md5_append(&state, (md5_byte_t *)"VT6PX?UQTM4WM%YR", 16);
+
md5_finish(&state, digest);
- sprintf(buf, "QRY %d msmsgs@msnmsgr.com 32\r\n", next_trid++);
+ sprintf(buf, "QRY %d PROD0038W!61ZTF9 32\r\n", next_trid++ );
+
write(conn->sock, buf, strlen(buf));
for(a=0; a<16; a++)
@@ -1591,8 +1624,426 @@
return inv;
}
+#define szUser info->username
+#define szPassword info->password
+
+int msn_login_read( int nSock, char *buf, int nMax )
+{
+ return cw_read( nSock, buf, nMax, 0 );
+}
+
+int msn_login_wait( int nSocket, char *szCommand )
+{
+ int nRet = 0;
+
+ while ( !nRet )
+ nRet = read( nSocket, szCommand, 1000 );
+
+ #ifdef MSNDEBUG
+ printf("<< %s", szCommand );
+ #endif
+
+ return 1;
+}
+
+void msn_login_write1( int nSocket, char *szString, char *szArg )
+{
+ char szWrite[ 1000 ];
+
+ // ext_debug( szString );
+ // ext_debug( szArg );
+
+ memset( szWrite, 0, 999 );
+ sprintf( szWrite, "%s %s\r\n", szString, szArg );
+
+ // ext_debug( szWrite );
+
+ cw_write( nSocket, szWrite, strlen( szWrite ), 0 );
+}
+
+void msn_login_write( int nSocket, char *szString )
+{
+ char szWrite[ 1000 ];
+
+ memset( szWrite, 0, 1000 );
+ sprintf( szWrite, "%s\r\n", szString );
+
+ cw_write( nSocket, szWrite, strlen( szWrite ), 0 );
+}
+
+int msn_login_connect( int nPort, char *szAddress )
+{
+ return ext_connect_socket( szAddress, nPort );
+}
+
+int msn_login_ssl_write( int nSock, char *str )
+{
+ return cw_write( nSock, str, strlen( str ), 1 );
+}
+
+int msn_login_ssl_read( int nSock, char *buf, int nMax )
+{
+ return cw_read( nSock, buf, nMax, 1 );
+}
+
+int msn_login_close( int nSock )
+{
+ return cw_close( nSock );
+}
+
+int msn_login_ssl_connect( int nPort, char *szAddr )
+{
+ return ext_connect_socket_ssl( szAddr, nPort );
+}
+
+int msn_login_get_server( char *str, char *filter, char *Server, char *Site )
+{
+ char *c, *c1, *c2;
+
+ c = strstr( str, filter );
+ if ( NULL == c )
+ return 0;
+ // Skip the "Filter="-part.
+ c++;
+ c += strlen( filter );
+ c1 = strchr( c, '/' );
+ if ( NULL == c1 )
+ return 0;
+ c2 = strchr( c1, ',' );
+ if ( NULL == c2 )
+ return 0;
+
+ strncpy( Server, c, (unsigned long)c1 - (unsigned long)c );
+ strncpy( Site, c1, (unsigned long)c2 - (unsigned long)c1 );
+
+ return 1;
+}
+
+int msnAuth( char *lc, char *ticket, char *user, char *password )
+{
+ int nexus; // Passport Login Nexus
+ int logins; // Login Server
+ char result[ 5000 ];
+ char result2[ 1000 ];
+ char Server[ 100 ]; // e.g. www.server.com
+ char Site[ 100 ]; // e.g. /site.html
+ char String[ 800 ];
+ int i;
+ char mail[ 255 ];
+ char name[ 255 ];
+
+ memset( mail, 0, 255 );
+ memset( name, 0, 255 );
+
+ for ( i = 0; i < strlen( user ); i++ )
+ {
+ if ( user[i] == '@' )
+ {
+ strncpy( name, user, i );
+ strcpy( mail, (char*)( (unsigned long)user + i + 1 ) );
+ break;
+ }
+ }
+
+ memset( Server, 0, 100 );
+ memset( Site, 0, 100 );
+
+ nexus = msn_login_ssl_connect( 443, "nexus.passport.com" );
+ msn_login_ssl_write( nexus, "GET /rdr/pprdr.asp HTTP/1.0\r\n\r\n" );
+ msn_login_ssl_read( nexus, result, 800 );
+ msn_login_close( nexus );
+ msn_login_get_server( result, "DALogin", Server, Site );
+
+ #ifdef MSNDEBUG
+ printf("Connecting to server '%s' .. site '%s'\n", Server, Site );
+ #endif
+
+ for ( ; ; )
+ {
+ // Connect to Login Server
+ logins = msn_login_ssl_connect( 443, Server );
+ memset( String, 0, 800 );
+ sprintf( String, "GET %s HTTP/1.1\r\n"
+ "Authorization: Passport1.4 OrgVerb=GET,OrgURL=http%%3A%%2F%%2Fmessenger%%2Emsn%%2Ecom,sign-in=%s%%40%s,pwd=%s,%s\r\n"
+ "Host: %s\r\n\r\n",
+ Site, name, mail, password, lc, Server );
+
+ #ifdef MSNDEBUG
+ printf("Writing: \n%s\n", String );
+ #endif
+
+ msn_login_ssl_write( logins, String );
+
+ memset( result, 0, 5000 );
+ memset( result2, 0, 1000 );
+
+ msn_login_ssl_read( logins, result, 5000 );
+ msn_login_ssl_read( logins, result2, 1000 );
+
+ strcat( result, result2 );
+
+ if ( strstr( result, "200 OK" ) )
+ {
+ char *tick;
+ char *c3, *c4;
+ // Okay.
+
+ tick = strstr( result, "t=" );
+ if ( NULL == tick )
+ {
+ #ifdef MSNDEBUG
+ printf("No t= found in response.\n");
+ #endif
+ return 0;
+ }
+
+ tick += 2;
+
+ c4 = strstr( tick, "," );
+
+ strncpy( ticket, tick, (unsigned long)c4 - (unsigned long)tick - 1 );
+
+ //msn_login_close( logins );
+ return 1;
+ }
+
+ if ( strstr( result, "302 Found") && strstr( result, "redir" ) && strstr( result, "Location: " ) )
+ {
+ // Redirection.
+ char *c3, *c4;
+
+ c3 = strstr( result, "Location: " );
+ c3 += 10;
+
+ c3 = strstr( c3, "https://" );
+ c3 += 8;
+
+ c4 = strstr( c3, "/" );
+ strncpy( Server, c3, (unsigned long)c4 - (unsigned long)c3 );
+ strncpy( Site, c4, (unsigned long)strchr( c4, '\r' ) - (unsigned long)c4 );
+
+ // printf("Redirection to server [%s] - Site [%s]\n", Server, Site );
+ msn_login_close( logins );
+ continue;
+ }
+
+ break;
+ }
+
+ // printf("Error\n");
+ return 0;
+}
+
+int msn_connect_v8_error( connectinfo *info, msnconn *conn, char *szErr )
+{
+ ext_show_error( NULL, szErr );
+ delete info;
+
+ if ( conn->sock != -1 )
+ {
+ ext_unregister_sock( conn->sock );
+ close( conn->sock );
+ conn->sock = -1;
+ }
+
+ return -1;
+}
+
+int msn_connect_v8( connectinfo *info, msnconn *conn, int *nNextTrid )
+{
+ int ds; // Dispatch Server
+ char result[ 1000 ];
+ char *c;
+ char szIp[ 20 ];
+ char szPort[ 20 ];
+ int nPort;
+ char lc[ 400 ];
+ char ticket[ 2000 ];
+
+ memset( result, 0, 500 );
+
+ ext_debug("MSNp8: finding login server");
+
+ // ds = msn_login_connect( 1863, "messenger.hotmail.com" );
+ ds = conn->sock;
+
+ // >> VER 1 MSNP8 CVR0\r\n
+ msn_login_write( ds, "VER 1 MSNP8 CVR0" );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "VER 1" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive VER 1)" );
+
+ // >> CVR 2 0x0409 win 4.10 i386 MSNMSGR 5.0.0544 MSMSGS something@something.com\r\n
+ // ext_debug( szUser );
+
+ msn_login_write1( ds, "CVR 2 0x0409 winnt 5.1 i386 MSNMSGR 5.0.0540 MSMSGS", szUser );
+
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "CVR 2" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive CVR 2)" );
+
+ // >> USR 3 TWN I something@something.com\r\n
+ msn_login_write1( ds, "USR 3 TWN I", szUser );
+ msn_login_wait( ds, result );
+ if ( !strstr( result, "XFR 3 NS " ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive XFR 3)" );
+
+ // Read MSN Server IP from message.
+ c = strstr( result, "NS ");
+ c += 3;
+ memset( szIp, 0, 20 );
+ memset( szPort, 0, 20 );
+ strncpy( szIp, c, (unsigned long)strchr( c, ':' ) - (unsigned long)c );
+ c = strchr( c, ':' ); c++;
+ strncpy( szPort, c, (unsigned long)strchr( c, ' ' ) - (unsigned long)c );
+ nPort = atoi( szPort );
+
+ // Close current socket.
+ msn_login_close( ds );
+ ext_unregister_sock( ds );
+ conn->sock = -1;
+
+ #ifdef MSNDEBUG
+ printf("* Connecting to IP `%s' port %d *\n", szIp, nPort );
+ #endif
+
+ ext_debug("MSNp8: found.. connecting");
+
+ // Try to connect to other server.
+ ds = msn_login_connect( nPort, szIp );
+ if ( ds <= 0 )
+ return msn_connect_v8_error( info, conn, "Error connecting to specified MSN Server" );
+
+ // OK. Register the socket.
+ conn->sock = ds;
+ ext_register_sock( ds, 1, 0 );
+
+ // >> VER 4 MSNP8 CVR0\r\n
+ msn_login_write( ds, "VER 4 MSNP8 CVR0" );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "VER 4" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive VER 4)" );
+
+ // >> CVR 5 0x0409 win 4.10 i386 MSNMSGR 5.0.0544 MSMSGS something@something.com\r\n
+ msn_login_write1( ds, "CVR 5 0x0409 winnt 5.1 i386 MSNMSGR 5.0.0540 MSMSGS", szUser );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "CVR 5" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive CVR 5)" );
+
+ // >> USR 6 TWN I something@something.com\r\n
+ msn_login_write1( ds, "USR 6 TWN I", szUser );
+ msn_login_wait( ds, result );
+
+ // << USR 6 TWN S something@something.com lc=....,....=...\r\n
+ if ( !strstr( result, "TWN S" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive TWS S)" );
+
+ memset( lc, 0, 400 );
+ c = strstr( result, "TWN S " );
+ c+=6;
+
+ strncpy( lc, c, (unsigned long)strchr(c, '\r') - (unsigned long)c );
+
+ #ifdef MSNDEBUG
+ printf("LC-etc string = `%s'\n", lc );
+ #endif
+
+ memset( ticket, 0, 2000 );
+
+ ext_debug("MSNp8: doing SSL auth");
+
+ if ( ! msnAuth( lc, ticket, szUser, szPassword ) )
+ {
+ // printf("Error #6\n");
+ return 0;
+ }
+
+ ext_debug("MSNp8: OK.. logging in");
+
+ #ifdef MSNDEBUG
+ printf("Ticket = `%s'\n", ticket );
+ #endif
+
+ memset( result, 0, 500 );
+ sprintf( result, "USR 7 TWN S t=%s", ticket );
+
+ // >> USR 7 TWN S t=<ticket>
+ msn_login_write( ds, result );
+ memset( result, 0, 500 );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "USR 7 OK") )
+ {
+ if ( result[ 0 ] >= '0' && result[ 0 ] <= '9' )
+ {
+ char *err;
+ int nCode = 0;
+ // We received an error code.
+
+ err = strchr( result, ' ' );
+ if ( NULL == err )
+ nCode = atoi( result );
+ else {
+ *err = '\0';
+ nCode = atoi( result );
+ }
+ if ( nCode <= 0 )
+ return msn_connect_v8_error( info, conn, "Protocol error (Invalid response after USR 7)" );
+ return nCode;
+ }
+
+ // Invalid response.
+ return msn_connect_v8_error( info, conn, "Protocol error (Invalid response after USR 7)" );
+ }
+
+ // We are now connected to the MSN Server
+
+ // msn_login_write( ds, "OUT" );
+ // msn_login_close( ds );
+
+ // << USR 7 OK something@something.com Something%20Friendly%Nick 1 0
+ {
+ char *szFriendly;
+ char *cEnd;
+ int i;
+
+ szFriendly = result;
+
+ for ( i = 0; i < 4; i++ )
+ {
+ szFriendly = strchr( szFriendly, ' ' );
+
+ if ( NULL == szFriendly )
+ {
+ ext_got_friendlyname( conn, "Unknown nickname" );
+ return 0;
+ }
+
+ szFriendly++;
+ }
+
+ cEnd = strchr( szFriendly, ' ');
+ if ( NULL != cEnd )
+ *cEnd = '\0';
+
+ // ext_debug( msn_decode_URL( szFriendly ) );
+ ext_got_friendlyname( conn, msn_decode_URL( szFriendly ) );
+ }
+
+ *nNextTrid = 8;
+
+ // No error.
+ return 0;
+}
+
void msn_connect(msnconn * conn, const char * server, int port)
{
+ int result;
+
conn->ready=0;
if(conn->type==CONN_SB)
@@ -1645,106 +2096,37 @@
ext_register_sock(conn->sock, 1, 0);
- #ifdef MSNDEBUG
- printf("Connected\n"); // DEBUG
- #endif
-
- sprintf(buf, "VER %d MSNP7\r\n", next_trid);
- write(conn->sock, buf, strlen(buf));
- msn_add_callback(conn, msn_connect_2, next_trid, (callback_data *)info);
- next_trid++;
-}
-
-// Further connection functions:
+ // Okay, now try to connect.
-void msn_connect_2(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
+ ext_debug("MSNp8: connecting to MSN.. this could take a few seconds");
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
+ result = msn_connect_v8( info, conn, &next_trid );
- if(strcmp(args[0], "VER") || strcmp(args[2], "MSNP7")) // if either *differs*...
+ if ( 0 != result )
{
- ext_show_error(NULL, "Protocol negotiation failed");
- delete info;
- ext_unregister_sock(conn->sock);
- close(conn->sock);
- conn->sock=-1;
- return;
- }
-
- sprintf(buf, "USR %d MD5 I %s\r\n", next_trid, info->username);
- write(conn->sock, buf, strlen(buf));
-
- msn_add_callback(conn, msn_connect_3, next_trid, data);
- next_trid++;
-}
-
-void msn_connect_3(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- md5_state_t state;
- md5_byte_t digest[16];
- int a;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
+ // Error code.
- if(isdigit(args[0][0]))
+ if ( result > 0 )
{
- msn_show_verbose_error(conn, atoi(args[0]));
- msn_clean_up(conn);
+ msn_show_verbose_error( conn, result );
delete info;
- return;
- }
+ msn_clean_up( conn );
+ conn->sock = -1;
- // OK, the challenge just arrived as args[4]
+ } // else: connection failed completely. msn_connect_v8 already took care of destroying the connection
- md5_init(&state);
- md5_append(&state, (md5_byte_t *)(args[4]), strlen(args[4]));
- md5_append(&state, (md5_byte_t *)(info->password), strlen(info->password));
- md5_finish(&state, digest);
-
- sprintf(buf, "USR %d MD5 S ", next_trid);
- write(conn->sock, buf, strlen(buf));
-
- for(a=0; a<16; a++)
- {
- sprintf(buf, "%02x", digest[a]);
- write(conn->sock, buf, 2);
}
-
- write(conn->sock, "\r\n", 2);
-
- msn_add_callback(conn, msn_connect_4, next_trid, data);
- next_trid++;
-}
-
-void msn_connect_4(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
-
- if(isdigit(args[0][0]))
+ else
{
- msn_show_verbose_error(conn, atoi(args[0]));
- delete info;
- msn_clean_up(conn);
- return;
- }
-
- ext_got_friendlyname(conn, msn_decode_URL(args[4]));
+ // We received no error code. Everything went ok!
delete info;
- next_trid++;
+ ext_debug("MSNp8: OK");
- conn->ready=1;
- ext_new_connection(conn);
+ conn->ready = 1;
+ ext_new_connection( conn );
+ }
}
void msn_SB_ans(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
@@ -1774,30 +2156,7 @@
void msn_set_state(msnconn * conn, const char * state)
{
- sprintf(buf, "CHG %d %s\r\n", next_trid, state);
+ sprintf(buf, "CHG %d %s %d\r\n", next_trid, state, MSN_VERSION_ID );
write(conn->sock, buf, strlen(buf));
next_trid++;
}
-
-/*
-void msn_connect_3(msnconn * conn, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
- trid++;
-
- if(isdigit(args[0][0]))
- {
- msn_print_verbose_error(conn, atoi(args[0]));
- delete info;
- return;
- }
-
- sprintf(buf, "INF %d\r\n", trid, info->username);
- write(conn.sock, buf, strlen(buf));
-
- msn_add_callback(conn, msn_connect_4, trid, data);
-}
-*/

View File

@ -1,123 +0,0 @@
--- blip-0.1/msn_core.h.orig Sat Dec 14 07:58:06 2002
+++ blip-0.1/msn_core.h Thu Oct 23 20:02:19 2003
@@ -24,6 +24,49 @@
~char_data() { if(c!=NULL) { delete c; } }
};
+class callback_data
+{};
+
+class callback : public llist_data
+{
+ public:
+ int trid;
+ void (*func)(struct msnconn * conn, int trid, char ** args, int numargs, callback_data * data);
+ callback_data * data; // just gets passed
+};
+
+// Intermediate steps in synchronisation
+class syncinfo : public callback_data
+{
+ public:
+
+ llist * fl;
+ llist * rl;
+ llist * al;
+ llist * bl;
+
+ unsigned int complete;
+
+ int serial;
+ int nContacts;
+ int nGroups;
+ int nFound;
+
+ char *last_user_handled;
+
+ char blp;
+ char gtc;
+
+ syncinfo() { nFound = 0; nContacts = 0; blp='A'; gtc='A'; fl=rl=al=bl=NULL; complete=0; serial=0; }
+ ~syncinfo()
+ {
+ if(fl!=NULL) { delete fl; }
+ if(rl!=NULL) { delete rl; }
+ if(al!=NULL) { delete al; }
+ if(bl!=NULL) { delete bl; }
+ }
+};
+
class message : public llist_data // This class encapsulates all that you need to know (tm) about a MSG
{
public:
@@ -81,14 +124,17 @@
public:
int sock; // Socket (durr...)
int type; // one of the #defines below
+ int sync; // syncing
int ready;
+
+ syncinfo *sync_info;
llist * users; // Users in this session - only for SB connections
llist * invitations_out; // invitations extended but not responded to
llist * invitations_in; // invitations received but not responded to
llist * callbacks;
authdata * auth;
- msnconn() { users=NULL; callbacks=NULL; invitations_out=NULL; invitations_in=NULL; }
+ msnconn() { sync = 0; users=NULL; callbacks=NULL; invitations_out=NULL; invitations_in=NULL; }
~msnconn()
{
if(users!=NULL) { delete users; }
@@ -177,17 +223,6 @@
#define MSNFTP_SEND 1
#define MSNFTP_RECV 2
-class callback_data
-{};
-
-class callback : public llist_data
-{
- public:
- int trid;
- void (*func)(struct msnconn * conn, int trid, char ** args, int numargs, callback_data * data);
- callback_data * data; // just gets passed
-};
-
extern llist * connections;
extern int next_trid;
@@ -224,33 +259,6 @@
#define COMPLETE_BLP 16
#define COMPLETE_GTC 32
-
-// Intermediate steps in synchronisation
-class syncinfo : public callback_data
-{
- public:
-
- llist * fl;
- llist * rl;
- llist * al;
- llist * bl;
-
- unsigned int complete;
-
- int serial;
-
- char blp;
- char gtc;
-
- syncinfo() { blp='A'; gtc='A'; fl=rl=al=bl=NULL; complete=0; serial=0; }
- ~syncinfo()
- {
- if(fl!=NULL) { delete fl; }
- if(rl!=NULL) { delete rl; }
- if(al!=NULL) { delete al; }
- if(bl!=NULL) { delete bl; }
- }
-};
void msn_set_friendlyname(msnconn * conn, const char * friendlyname);

View File

@ -1,20 +0,0 @@
--- blip-0.1/msn_interface.h.orig Mon Dec 9 20:31:41 2002
+++ blip-0.1/msn_interface.h Thu Oct 23 20:02:19 2003
@@ -25,6 +25,8 @@
void ext_got_info(msnconn * conn, syncinfo * data);
+void ext_debug( char *msg );
+
void ext_latest_serial(msnconn * conn, int serial);
void ext_got_GTC(msnconn * conn, char c);
@@ -78,6 +80,8 @@
Return: Nothing
*/
int ext_connect_socket(const char * server, int port);
+
+int ext_connect_socket_ssl(const char * server, int port);
int ext_server_socket(int port);

View File

@ -1,98 +0,0 @@
--- src/hooks/msnhook.cc.orig Tue Sep 30 19:38:43 2003
+++ src/hooks/msnhook.cc Thu Oct 23 20:12:58 2003
@@ -120,11 +120,14 @@
face.log(_("+ [msn] connecting to the server"));
+ flogged = false;
+ fonline = true;
+
msn_init(&conn, nicknormalize(account.nickname).c_str(), account.password.c_str());
msn_connect(&conn, account.server.c_str(), account.port);
fonline = true;
- flogged = false;
+ flogged = true;
}
void msnhook::disconnect() {
@@ -248,7 +251,7 @@
}
icqcontact *c = clist.get(ev.getcontact());
- text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf8");
+ text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf-8");
if(c)
if(c->getstatus() != offline || !c->inlist()) {
@@ -378,11 +381,11 @@
void msnhook::checkfriendly(icqcontact *c, const string friendlynick, bool forcefetch) {
string oldnick = c->getnick();
- string newnick = unmime(friendlynick);
+ string newnick = siconv(unmime(friendlynick), "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
c->setnick(newnick);
- if(forcefetch || (oldnick != newnick && c->getdispnick() == oldnick) || oldnick.empty()) {
+ if(forcefetch || (oldnick != newnick && c->getdispnick() != oldnick) || oldnick.empty()) {
c->setdispnick(newnick);
face.relaxedupdate();
}
@@ -450,6 +453,12 @@
#endif
}
+int ext_debug( char *str )
+{
+ log( str );
+ return 0;
+}
+
void ext_register_sock(int s, int reading, int writing) {
log("ext_register_sock");
if(reading) mhook.rfds.push_back(s);
@@ -602,7 +611,7 @@
mhook.checkinlist(ic);
- string text = siconv(msg->body, "utf8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+ string text = siconv(msg->body, "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
em.store(immessage(ic, imevent::incoming, text));
}
@@ -710,8 +719,7 @@
log("ext_changed_state");
}
-int ext_connect_socket(const char *hostname, int port) {
- log("ext_connect_socket");
+int ext_do_connect_socket(const char *hostname, int port, int ssl) {
struct sockaddr_in sa;
struct hostent *hp;
int a, s;
@@ -732,13 +740,23 @@
if((s = socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0)
return -1;
- if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), 0) < 0) {
+ if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), ssl) < 0) {
face.log(msgerr + _("verify the hostname and port"));
close(s);
return -1;
}
return s;
+}
+
+int ext_connect_socket_ssl(const char *hostname, int port) {
+ log("ext_connect_socket_ssl");
+ return ext_do_connect_socket(hostname, port, 1);
+}
+
+int ext_connect_socket(const char *hostname, int port) {
+ log("ext_connect_socket");
+ return ext_do_connect_socket(hostname, port, 0);
}
int ext_server_socket(int port) {

View File

@ -1,7 +0,0 @@
--- src/Makefile.in.orig Thu May 8 14:58:44 2003
+++ src/Makefile.in Thu May 8 14:58:57 2003
@@ -98,3 +98,3 @@
centericq_LDFLAGS = -L$(top_srcdir)/blip-0.1 -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1
-centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lblip -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@
+centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lblip -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@ -lintl
SUBDIRS = hooks

View File

@ -1,11 +0,0 @@
--- src/hooks/yahoohook.cc.orig Fri Oct 3 03:55:06 2003
+++ src/hooks/yahoohook.cc Wed Oct 8 17:29:21 2003
@@ -556,7 +556,7 @@
string yahoohook::decode(const string &text, bool utf) {
if(utf)
- return siconv(text, "utf8",
+ return siconv(text, "utf-8",
conf.getrussian(proto) ? "koi8-u" : conf.getdefcharset());
return rushtmlconv("wk", text);

View File

@ -1,5 +1,5 @@
Centericq is a text mode menu- and window-driven IM interface that
supports the ICQ2000, Yahoo!, AIM, MSN and IRC protocols. It allows you
supports the ICQ2000, Yahoo!, AIM, and IRC protocols. It allows you
to send, receive, and forward messages, URLs, SMSes, contacts, and email
express messages. It also lets you set your own and fetch others' away
messages, and define external handlers for incoming events. You can
@ -11,4 +11,6 @@ inactivity, and have your own ignore, visible, and invisible lists.
It can also associate events with sounds, make log of events, and
allows arrangement of contacts into groups.
Note: MSN protocol is not supported offcially.
WWW: http://konst.org.ua/centericq/

View File

@ -7,8 +7,8 @@
#
PORTNAME= centericq
PORTVERSION= 4.9.7
PORTREVISION= 3
PORTVERSION= 4.9.8
PORTREVISION= 0
CATEGORIES= net
MASTER_SITES= http://centericq.de/archive/source/releases/
@ -18,8 +18,6 @@ COMMENT= A text mode menu- and window-driven IM interface
LIB_DEPENDS= intl.5:${PORTSDIR}/devel/gettext \
iconv.3:${PORTSDIR}/converters/libiconv
BROKEN= Does not fetch, will be removed after Feb 2
USE_OPENSSL= yes
USE_GMAKE= yes
GNU_CONFIGURE= yes
@ -33,8 +31,22 @@ LIB_DEPENDS+= fribidi.0:${PORTSDIR}/converters/fribidi
CONFIGURE_ARGS+= --with-fribidi
.endif
.if !defined(WITH_MSN)
CONFIGURE_ARGS+= --disable-msn
.if defined(WITH_MSN)
CONFIGURE_ARGS+= --enable-msn
EXTRA_PATCHES= ${.CURDIR}/files/msn-*
pre-patch:
@${ECHO_CMD} "========================================================="
@${ECHO_CMD} "=====================Important !!!======================="
@${ECHO_CMD} "========================================================="
@${ECHO_CMD} "There may be some sticky legal issues with the new"
@${ECHO_CMD} "version of this protocol. Users should be aware that they"
@${ECHO_CMD} "might be in violation of the DMCA or other laws. If this"
@${ECHO_CMD} "is unacceptable, hit Ctrl-C now and remove WITH_MSN from"
@${ECHO_CMD} "your make flags. The FreeBSD group assumes no"
@${ECHO_CMD} "responsibility or liability for any losses or damages"
@${ECHO_CMD} "sustained by use or disuse of software in the ports tree."
@${ECHO_CMD} "========================================================="
@sleep 5
.endif
.if !defined(WITH_YAHOO)
@ -61,7 +73,7 @@ CONFIGURE_ARGS+= --disable-rss
CONFIGURE_ARGS+= --disable-lj
.endif
MAN1= centericq.1 cicqconv.1 cicqsync.1
MAN1= cicqconv.1 cicqsync.1
post-patch:
.for file in kkconsui-0.1/include/conf.h kkstrtext-0.1/conf.h kksystr-0.1/include/conf.h

View File

@ -1 +1 @@
MD5 (centericq-4.9.7.tar.gz) = 09c1672c0c2e5ef7e8a94052a71c58cc
MD5 (centericq-4.9.8.tar.gz) = 94e605d33f0dec7619bdfe6dad7b7a33

View File

@ -0,0 +1,32 @@
--- Makefile.in.orig Sat Oct 25 15:53:45 2003
+++ Makefile.in Mon Nov 3 20:14:01 2003
@@ -92,10 +92,10 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-SUBDIRS = firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 intl po contrib misc share src
+SUBDIRS = blip-0.1 firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 intl po contrib misc share src
# END OF MOTOR DIST TARGETS #
-EXTRA_DIST = centericq.1 centericq.motor config.rpath FAQ NEWS TODO README THANKS AUTHORS INSTALL ABOUT-NLS ChangeLog COPYING centericq.spec firetalk-0.1/* kkconsui-0.1/* kkstrtext-0.1/* libicq2000-0.1/* libjabber-0.1/* libyahoo2-0.1/* kksystr-0.1/* connwrap-0.1/*
+EXTRA_DIST = centericq.1 centericq.motor config.rpath FAQ NEWS TODO README THANKS AUTHORS INSTALL ABOUT-NLS ChangeLog COPYING centericq.spec blip-0.1/* firetalk-0.1/* kkconsui-0.1/* kkstrtext-0.1/* libicq2000-0.1/* libjabber-0.1/* libyahoo2-0.1/* kksystr-0.1/* connwrap-0.1/*
AUTOMAKE_OPTIONS = foreign
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
@@ -289,6 +289,7 @@
cd $(top_srcdir) \
&& $(AUTOMAKE) --include-deps --build-dir=$$here --srcdir-name=$(top_srcdir) --output-dir=$$top_distdir --foreign Makefile
$(mkinstalldirs) $(distdir)/connwrap-0.1 $(distdir)/firetalk-0.1 \
+ $(distdir)/blip-0.1 \
$(distdir)/kkconsui-0.1 $(distdir)/kkstrtext-0.1 \
$(distdir)/kksystr-0.1 $(distdir)/libicq2000-0.1 \
$(distdir)/libjabber-0.1 $(distdir)/libyahoo2-0.1
@@ -388,7 +389,7 @@
dist-hook:
cd $(top_distdir); subs=`egrep "^[:space:]*SUBDIRS" Makefile.am | sed 's/SUBDIRS[ =]\+//g'`; \
- echo "SUBDIRS = firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 $$subs" >>.makefile.am; \
+ echo "SUBDIRS = blip-0.1 firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 $$subs" >>.makefile.am; \
egrep -v "^[:space:]*SUBDIRS" Makefile.am >>.makefile.am; \
mv .makefile.am Makefile.am; autoconf && automake

View File

@ -0,0 +1,20 @@
--- src/hooks/abstracthook.cc.orig Sun Oct 19 06:57:26 2003
+++ src/hooks/abstracthook.cc Mon Nov 3 19:54:31 2003
@@ -31,6 +31,7 @@
#include "jabberhook.h"
#include "rsshook.h"
#include "ljhook.h"
+#include "msnhook.h"
#include "md5.h"
@@ -325,6 +326,9 @@
#endif
#ifdef BUILD_LJ
case livejournal: return lhook;
+#endif
+#ifdef BUILD_MSN
+ case msn: return mhook;
#endif
}

View File

@ -0,0 +1,12 @@
--- config.h.in.orig Thu Oct 16 06:07:45 2003
+++ config.h.in Mon Nov 3 21:31:23 2003
@@ -220,6 +220,9 @@
/* use gnutls */
#undef HAVE_GNUTLS
+/* build with msn support */
+#undef BUILD_MSN
+
/* build with yahoo support */
#undef BUILD_YAHOO

View File

@ -0,0 +1,72 @@
--- configure.orig Sat Oct 25 15:53:45 2003
+++ configure Mon Nov 3 20:21:06 2003
@@ -27,6 +27,8 @@
ac_help="$ac_help
--with-libgnutls-extra-prefix=PFX Prefix where libgnutls-extra is installed (optional)"
ac_help="$ac_help
+ --enable-msn Build with MSN!"
+ac_help="$ac_help
--disable-yahoo Build without Yahoo!"
ac_help="$ac_help
--disable-aim Build without AIM"
@@ -2365,6 +2367,14 @@
;;
esac
+# Check whether --enable-msn or --disable-msn was given.
+if test "${enable_msn+set}" = set; then
+ enableval="$enable_msn"
+ build_msn="$enableval"
+else
+ build_msn="yes"
+fi
+
# Check whether --enable-yahoo or --disable-yahoo was given.
if test "${enable_yahoo+set}" = set; then
enableval="$enable_yahoo"
@@ -2424,6 +2434,13 @@
+if test "x$build_msn" = xyes; then
+ BUILD_MSN_TRUE=
+ BUILD_MSN_FALSE='#'
+else
+ BUILD_MSN_TRUE='#'
+ BUILD_MSN_FALSE=
+fi
if test "x$build_yahoo" = xyes; then
BUILD_YAHOO_TRUE=
@@ -2478,6 +2495,13 @@
BUILD_LJ_FALSE=
fi
+if test "$build_msn" = "yes"; then
+ cat >> confdefs.h <<\EOF
+#define BUILD_MSN 1
+EOF
+
+fi
+
if test "$build_yahoo" = "yes"; then
cat >> confdefs.h <<\EOF
#define BUILD_YAHOO 1
@@ -4994,7 +5018,7 @@
-subdirs="firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1"
+subdirs="firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 blip-0.1"
trap '' 1 2 15
cat > confcache <<\EOF
@@ -5538,7 +5562,7 @@
esac
done
- for ac_config_dir in firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1; do
+ for ac_config_dir in firetalk-0.1 kkconsui-0.1 kkstrtext-0.1 libicq2000-0.1 libjabber-0.1 libyahoo2-0.1 kksystr-0.1 connwrap-0.1 blip-0.1; do
# Do not complain, so a configure script can configure whichever
# parts of a large source tree are present.

View File

@ -0,0 +1,10 @@
--- src/imcontroller.cc.orig Thu Oct 16 07:40:18 2003
+++ src/imcontroller.cc Mon Nov 3 20:03:55 2003
@@ -31,6 +31,7 @@
#include "jabberhook.h"
#include "icqcontacts.h"
#include "eventmanager.h"
+#include "msnhook.h"
#define clr(c) conf.getcolor(c)

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,804 @@
--- src/hooks/msnhook.cc.orig Mon Nov 3 20:25:37 2003
+++ src/hooks/msnhook.cc Mon Nov 3 20:24:20 2003
@@ -0,0 +1,801 @@
+/*
+*
+* centericq MSN protocol handling class
+* $Id: msnhook.cc,v 1.67 2003/09/30 11:38:43 konst Exp $
+*
+* Copyright (C) 2001 by Konstantin Klyagin <konst@konst.org.ua>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or (at
+* your option) any later version.
+*
+* This program is distributed in the hope that it will be useful, but
+* WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+* General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+* USA
+*
+*/
+
+#include "icqcommon.h"
+
+#ifdef BUILD_MSN
+
+#include "msnhook.h"
+#include "icqconf.h"
+#include "icqface.h"
+#include "icqcontacts.h"
+#include "accountmanager.h"
+#include "eventmanager.h"
+#include "imlogger.h"
+#include "connwrap.h"
+
+#include "msn_bittybits.h"
+
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <netdb.h>
+#include <arpa/inet.h>
+
+msnhook mhook;
+
+static string nicknormalize(const string &nick) {
+ if(nick.find("@") == -1) return nick + "@hotmail.com";
+ return nick;
+}
+
+static string nicktodisp(const string &nick) {
+ int pos;
+ string r = nick;
+
+ if((pos = r.find("@")) != -1)
+ if(r.substr(pos+1) == "hotmail.com")
+ r.erase(pos);
+
+ return r;
+}
+
+struct st2imr {
+ char *name;
+ imstatus st;
+};
+
+const st2imr st2im[] = {
+ { "FLN", offline },
+ { "NLN", available },
+ { "HDN", invisible },
+ { "BSY", dontdisturb },
+ { "PHN", occupied },
+ { "AWY", away },
+ { "BRB", away },
+ { "LUN", notavail },
+ { "IDL", away },
+ { 0, offline }
+};
+
+static imstatus msn2imstatus(const string &sname) {
+ for(const st2imr *sa = st2im; sa->name; sa++)
+ if(sname == sa->name)
+ return sa->st;
+
+ return offline;
+}
+
+static const char *stat2name(imstatus st) {
+ for(const st2imr *sa = st2im; sa->name; sa++)
+ if(st == sa->st)
+ return sa->name;
+
+ return "NLN";
+}
+
+// ----------------------------------------------------------------------------
+
+msnhook::msnhook(): abstracthook(msn) {
+ ourstatus = offline;
+ fonline = false;
+
+ fcapabs.insert(hookcapab::synclist);
+ fcapabs.insert(hookcapab::changedetails);
+ fcapabs.insert(hookcapab::directadd);
+// fcapabs.insert(hookcapab::files);
+}
+
+msnhook::~msnhook() {
+}
+
+void msnhook::init() {
+ manualstatus = conf.getstatus(msn);
+}
+
+void msnhook::connect() {
+ icqconf::imaccount account = conf.getourid(msn);
+
+ face.log(_("+ [msn] connecting to the server"));
+
+ flogged = false;
+ fonline = true;
+
+ msn_init(&conn, nicknormalize(account.nickname).c_str(), account.password.c_str());
+ msn_connect(&conn, account.server.c_str(), account.port);
+
+ fonline = true;
+ flogged = true;
+}
+
+void msnhook::disconnect() {
+ msn_clean_up(&conn);
+}
+
+void msnhook::exectimers() {
+}
+
+void msnhook::main() {
+ vector<int>::const_iterator i;
+ fd_set rs, ws;
+ struct timeval tv;
+ int hsock;
+
+ FD_ZERO(&rs);
+ FD_ZERO(&ws);
+
+ tv.tv_sec = tv.tv_usec = 0;
+ hsock = 0;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i) {
+ FD_SET(*i, &rs);
+ hsock = max(hsock, *i);
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i) {
+ FD_SET(*i, &ws);
+ hsock = max(hsock, *i);
+ }
+
+ if(select(hsock+1, &rs, &ws, 0, &tv) > 0) {
+ for(i = rfds.begin(); i != rfds.end(); ++i)
+ if(FD_ISSET(*i, &rs)) {
+ msn_handle_incoming(*i, 1, 0);
+ return;
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i)
+ if(FD_ISSET(*i, &ws)) {
+ msn_handle_incoming(*i, 0, 1);
+ return;
+ }
+ }
+}
+
+void msnhook::getsockets(fd_set &rf, fd_set &wf, fd_set &efds, int &hsocket) const {
+ vector<int>::const_iterator i;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i) {
+ hsocket = max(hsocket, *i);
+ FD_SET(*i, &rf);
+ }
+
+ for(i = wfds.begin(); i != wfds.end(); ++i) {
+ hsocket = max(hsocket, *i);
+ FD_SET(*i, &wf);
+ }
+}
+
+bool msnhook::isoursocket(fd_set &rf, fd_set &wf, fd_set &efds) const {
+ vector<int>::const_iterator i;
+
+ for(i = rfds.begin(); i != rfds.end(); ++i)
+ if(FD_ISSET(*i, &rf))
+ return true;
+
+ for(i = wfds.begin(); i != wfds.end(); ++i)
+ if(FD_ISSET(*i, &wf))
+ return true;
+
+ return false;
+}
+
+bool msnhook::online() const {
+ return fonline;
+}
+
+bool msnhook::logged() const {
+ return fonline && flogged;
+}
+
+bool msnhook::isconnecting() const {
+ return fonline && !flogged;
+}
+
+bool msnhook::enabled() const {
+ return true;
+}
+
+bool msnhook::send(const imevent &ev) {
+ string text;
+
+ if(ev.gettype() == imevent::message) {
+ const immessage *m = static_cast<const immessage *>(&ev);
+ if(m) text = m->gettext();
+
+ } else if(ev.gettype() == imevent::url) {
+ const imurl *m = static_cast<const imurl *>(&ev);
+ if(m) text = m->geturl() + "\n\n" + m->getdescription();
+
+ } else if(ev.gettype() == imevent::file) {
+ const imfile *m = static_cast<const imfile *>(&ev);
+ vector<imfile::record> files = m->getfiles();
+ vector<imfile::record>::const_iterator ir;
+
+ for(ir = files.begin(); ir != files.end(); ++ir) {
+ imfile::record r;
+ invitation_ftp *p;
+
+ r.fname = ir->fname;
+ r.size = ir->size;
+
+ imfile fr(ev.getcontact(), imevent::outgoing, "", vector<imfile::record>(1, r));
+
+ if(p = msn_filetrans_send(&conn, ir->fname.c_str()))
+ transferinfo[fr].first = p;
+ }
+
+ return true;
+ }
+
+ icqcontact *c = clist.get(ev.getcontact());
+ text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf-8");
+
+ if(c)
+ if(c->getstatus() != offline || !c->inlist()) {
+ msn_send_IM(&conn, nicknormalize(ev.getcontact().nickname).c_str(), text.c_str());
+ return true;
+ }
+
+ return false;
+}
+
+void msnhook::sendnewuser(const imcontact &ic) {
+ if(logged()) {
+ icqcontact *c;
+ imcontact icc(nicktodisp(ic.nickname), msn);
+
+ if(icc.nickname != ic.nickname)
+ if(c = clist.get(ic)) {
+ c->setdesc(icc);
+ c->setnick(icc.nickname);
+ c->setdispnick(icc.nickname);
+ }
+
+ msn_add_to_list(&conn, "FL", nicknormalize(ic.nickname).c_str());
+ }
+
+ requestinfo(ic);
+}
+
+void msnhook::setautostatus(imstatus st) {
+ if(st != offline) {
+ if(getstatus() == offline) {
+ connect();
+ } else {
+ logger.putourstatus(msn, ourstatus, st);
+ msn_set_state(&conn, stat2name(ourstatus = st));
+ }
+ } else {
+ if(getstatus() != offline) {
+ disconnect();
+ }
+ }
+}
+
+imstatus msnhook::getstatus() const {
+ return online() ? ourstatus : offline;
+}
+
+void msnhook::removeuser(const imcontact &ic) {
+ removeuser(ic, true);
+}
+
+void msnhook::removeuser(const imcontact &ic, bool report) {
+ if(online()) {
+ if(report)
+ face.log(_("+ [msn] removing %s from the contacts"), ic.nickname.c_str());
+
+ msn_del_from_list(&conn, "FL", nicknormalize(ic.nickname).c_str());
+ }
+}
+
+void msnhook::requestinfo(const imcontact &ic) {
+ icqcontact *c = clist.get(ic);
+
+ if(!c) {
+ c = clist.get(contactroot);
+ c->clear();
+ }
+
+ icqcontact::moreinfo m = c->getmoreinfo();
+ icqcontact::basicinfo b = c->getbasicinfo();
+
+ b.email = nicknormalize(ic.nickname);
+ m.homepage = "http://members.msn.com/" + b.email;
+
+ if(ic.nickname == conf.getourid(msn).nickname)
+ c->setnick(friendlynicks[ic.nickname]);
+
+ c->setmoreinfo(m);
+ c->setbasicinfo(b);
+}
+
+void msnhook::lookup(const imsearchparams &params, verticalmenu &dest) {
+ if(params.reverse) {
+ vector<pair<string, string> >::const_iterator i = slst["RL"].begin();
+
+ while(i != slst["RL"].end()) {
+ icqcontact *c = new icqcontact(imcontact(nicktodisp(i->first), msn));
+ c->setnick(i->second);
+
+ dest.additem(conf.getcolor(cp_clist_msn), c, (string) " " + i->first);
+ ++i;
+ }
+ face.findready();
+
+ face.log(_("+ [msn] reverse users listing finished, %d found"),
+ slst["RL"].size());
+
+ dest.redraw();
+ }
+}
+
+vector<icqcontact *> msnhook::getneedsync() {
+ int i;
+ vector<icqcontact *> r;
+ bool found;
+
+ for(i = 0; i < clist.count; i++) {
+ icqcontact *c = (icqcontact *) clist.at(i);
+
+ if(c->getdesc().pname == msn) {
+ vector<pair<string, string> >::const_iterator fi = slst["FL"].begin();
+
+ for(found = false; fi != slst["FL"].end() && !found; ++fi)
+ found = c->getdesc().nickname == fi->first;
+
+ if(!found)
+ r.push_back(c);
+ }
+ }
+
+ return r;
+}
+
+void msnhook::sendupdateuserinfo(const icqcontact &c) {
+ msn_set_friendlyname(&conn, c.getnick().c_str());
+}
+
+void msnhook::checkfriendly(icqcontact *c, const string friendlynick, bool forcefetch) {
+ string oldnick = c->getnick();
+ string newnick = siconv(unmime(friendlynick), "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+
+ c->setnick(newnick);
+
+ if(forcefetch || (oldnick != newnick && c->getdispnick() != oldnick) || oldnick.empty()) {
+ c->setdispnick(newnick);
+ face.relaxedupdate();
+ }
+}
+
+void msnhook::checkinlist(imcontact ic) {
+ icqcontact *c = clist.get(ic);
+ vector<icqcontact *> notremote = getneedsync();
+
+ if(c)
+ if(c->inlist())
+ if(find(notremote.begin(), notremote.end(), c) != notremote.end())
+ mhook.sendnewuser(ic);
+}
+
+bool msnhook::knowntransfer(const imfile &fr) const {
+ return transferinfo.find(fr) != transferinfo.end();
+}
+
+void msnhook::replytransfer(const imfile &fr, bool accept, const string &localpath) {
+ if(accept) {
+ transferinfo[fr].second = localpath;
+
+ if(transferinfo[fr].second.substr(transferinfo[fr].second.size()-1) != "/")
+ transferinfo[fr].second += "/";
+
+ transferinfo[fr].second += justfname(fr.getfiles().begin()->fname);
+ msn_filetrans_accept(transferinfo[fr].first, transferinfo[fr].second.c_str());
+
+ } else {
+ msn_filetrans_reject(transferinfo[fr].first);
+ transferinfo.erase(fr);
+
+ }
+}
+
+void msnhook::aborttransfer(const imfile &fr) {
+ msn_filetrans_reject(transferinfo[fr].first);
+
+ face.transferupdate(fr.getfiles().begin()->fname, fr,
+ icqface::tsCancel, 0, 0);
+
+ transferinfo.erase(fr);
+}
+
+bool msnhook::getfevent(invitation_ftp *fhandle, imfile &fr) {
+ map<imfile, pair<invitation_ftp *, string> >::const_iterator i = transferinfo.begin();
+
+ while(i != transferinfo.end()) {
+ if(i->second.first == fhandle) {
+ fr = i->first;
+ return true;
+ }
+ ++i;
+ }
+
+ return false;
+}
+
+// ----------------------------------------------------------------------------
+
+static void log(const string &s) {
+#ifdef DEBUG
+ face.log(s);
+#endif
+}
+
+int ext_debug( char *str )
+{
+ log( str );
+ return 0;
+}
+
+void ext_register_sock(int s, int reading, int writing) {
+ log("ext_register_sock");
+ if(reading) mhook.rfds.push_back(s);
+ if(writing) mhook.wfds.push_back(s);
+}
+
+void ext_unregister_sock(int s) {
+ log("ext_unregister_sock");
+ vector<int>::iterator i;
+
+ i = find(mhook.rfds.begin(), mhook.rfds.end(), s);
+ if(i != mhook.rfds.end()) mhook.rfds.erase(i);
+
+ i = find(mhook.wfds.begin(), mhook.wfds.end(), s);
+ if(i != mhook.wfds.end()) mhook.wfds.erase(i);
+}
+
+void ext_got_friendlyname(msnconn * conn, const char * friendlyname) {
+ log("ext_got_friendlyname");
+
+ if(friendlyname)
+ if(strlen(friendlyname))
+ mhook.friendlynicks[conf.getourid(msn).nickname] = friendlyname;
+}
+
+void ext_got_info(msnconn *conn, syncinfo *info) {
+ log("ext_got_info");
+
+ userdata *ud;
+ llist *lst, *pl;
+ imcontact ic;
+
+ for(lst = info->fl; lst; lst = lst->next) {
+ ud = (userdata *) lst->data;
+
+ mhook.slst["FL"].push_back(make_pair(ud->username, ud->friendlyname));
+
+ ic = imcontact(nicktodisp(ud->username), msn);
+ icqcontact *c = clist.get(ic);
+ if(!c) c = clist.addnew(ic, false);
+
+ icqcontact::basicinfo bi = c->getbasicinfo();
+ icqcontact::workinfo wi = c->getworkinfo();
+
+ for(pl = ud->phone; pl; pl = pl->next) {
+ phonedata *pd = (phonedata *) pl->data;
+ string title = pd->title ? pd->title : "";
+
+ if(pd->number)
+ if(strlen(pd->number)) {
+ if(title == "PHH") bi.phone = pd->number; else
+ if(title == "PHW") wi.phone = pd->number; else
+ if(title == "PHM") bi.cellular = pd->number;
+ }
+ }
+
+ c->setbasicinfo(bi);
+ c->setworkinfo(wi);
+ }
+
+ for(lst = info->rl; lst; lst = lst->next) {
+ ud = (userdata *) lst->data;
+ mhook.slst["RL"].push_back(make_pair(ud->username, ud->friendlyname));
+ }
+
+ mhook.setautostatus(mhook.ourstatus);
+}
+
+void ext_latest_serial(msnconn * conn, int serial) {
+ log("ext_latest_serial");
+}
+
+void ext_got_GTC(msnconn * conn, char c) {
+ log("ext_got_GTC");
+}
+
+void ext_got_BLP(msnconn * conn, char c) {
+ log("ext_got_BLP");
+}
+
+void ext_new_RL_entry(msnconn *conn, const char *username, const char *friendlyname) {
+ log("ext_new_RL_entry");
+ msn_add_to_list(&mhook.conn, "AL", username);
+
+ imcontact ic(nicktodisp(username), msn);
+ mhook.checkinlist(ic);
+ em.store(imnotification(ic, _("The user has added you to his/her contact list")));
+}
+
+void ext_new_list_entry(msnconn *conn, const char *lst, const char *username) {
+ log("ext_new_list_entry");
+ mhook.slst[lst].push_back(make_pair(username, string()));
+}
+
+void ext_del_list_entry(msnconn *conn, const char *lst, const char *username) {
+ log("ext_del_list_entry");
+
+ vector<pair<string, string> >::iterator i = mhook.slst[lst].begin();
+ while(i != mhook.slst[lst].end()) {
+ if(i->first == username) {
+ mhook.slst[lst].erase(i);
+ i = mhook.slst[lst].begin();
+ } else {
+ ++i;
+ }
+ }
+}
+
+void ext_show_error(msnconn * conn, const char * msg) {
+ log("ext_show_error");
+ log(msg);
+}
+
+void ext_buddy_set(msnconn * conn, const char * buddy, const char * friendlyname, const char * status) {
+ log("ext_buddy_set");
+ imcontact ic(nicktodisp(buddy), msn);
+ icqcontact *c = clist.get(ic);
+ bool forcefetch;
+
+ if(forcefetch = !c)
+ c = clist.addnew(ic, false);
+
+ if(friendlyname)
+ mhook.checkfriendly(c, friendlyname, forcefetch);
+
+ logger.putonline(ic, c->getstatus(), msn2imstatus(status));
+ c->setstatus(msn2imstatus(status));
+}
+
+void ext_buddy_offline(msnconn * conn, const char * buddy) {
+ log("ext_buddy_offline");
+ ext_buddy_set(conn, buddy, 0, "FLN");
+}
+
+void ext_got_SB(msnconn * conn, void * tag) {
+ log("ext_got_SB");
+}
+
+void ext_user_joined(msnconn *conn, const char *username, const char *friendlyname, int is_initial) {
+ log("ext_user_joined");
+}
+
+void ext_user_left(msnconn *conn, const char *username) {
+ log("ext_user_left");
+}
+
+void ext_got_IM(msnconn *conn, const char *username, const char *friendlyname, message *msg) {
+ log("ext_got_IM");
+ imcontact ic(nicktodisp(username), msn);
+
+ mhook.checkinlist(ic);
+
+ string text = siconv(msg->body, "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+ em.store(immessage(ic, imevent::incoming, text));
+}
+
+void ext_IM_failed(msnconn *conn) {
+ log("ext_IM_failed");
+}
+
+void ext_typing_user(msnconn *conn, const char *username, const char *friendlyname) {
+ log("ext_typing_user");
+ icqcontact *c = clist.get(imcontact(nicktodisp(username), msn));
+ if(c) c->setlasttyping(timer_current);
+}
+
+void ext_initial_email(msnconn *conn, int unread_inbox, int unread_folders) {
+ log("ext_initial_email");
+
+ face.log(_("+ [msn] unread e-mail: %d in inbox, %d in folders"),
+ unread_inbox, unread_folders);
+}
+
+void ext_new_mail_arrived(msnconn *conn, const char *from, const char *subject) {
+ log("ext_new_mail_arrived");
+
+ face.log(_("+ [msn] e-mail from %s, %s"), from, subject);
+ clist.get(contactroot)->playsound(imevent::email);
+}
+
+void ext_filetrans_invite(msnconn *conn, const char *username, const char *friendlyname, invitation_ftp *inv) {
+ log("ext_filetrans_invite");
+
+ if(!mhook.fcapabs.count(hookcapab::files))
+ return;
+
+ imfile::record r;
+ r.fname = inv->filename;
+ r.size = inv->filesize;
+
+ imcontact ic(nicktodisp(username), msn);
+ mhook.checkinlist(ic);
+
+ imfile fr(ic, imevent::incoming, "", vector<imfile::record>(1, r));
+
+ mhook.transferinfo[fr].first = inv;
+ em.store(fr);
+
+ face.transferupdate(inv->filename, fr, icqface::tsInit, inv->filesize, 0);
+}
+
+void ext_filetrans_progress(invitation_ftp *inv, const char *status, unsigned long sent, unsigned long total) {
+ log("ext_filetrans_progress");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr,
+ icqface::tsProgress, total, sent);
+ }
+}
+
+void ext_filetrans_failed(invitation_ftp *inv, int error, const char *message) {
+ log("ext_filetrans_failed");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr, icqface::tsError, 0, 0);
+ mhook.transferinfo.erase(fr);
+ }
+}
+
+void ext_filetrans_success(invitation_ftp *inv) {
+ log("ext_filetrans_success");
+ imfile fr;
+
+ if(mhook.getfevent(inv, fr)) {
+ face.transferupdate(fr.getfiles().begin()->fname, fr, icqface::tsFinish, 0, 0);
+ mhook.transferinfo.erase(fr);
+ }
+}
+
+void ext_new_connection(msnconn *conn) {
+ log("ext_new_connection");
+ if(conn->type == CONN_NS) {
+ msn_sync_lists(conn, 0);
+ logger.putourstatus(msn, offline, mhook.ourstatus = mhook.manualstatus);
+ mhook.flogged = true;
+ face.log(_("+ [msn] logged in"));
+ face.update();
+ }
+}
+
+void ext_closing_connection(msnconn *conn) {
+ log("ext_closing_connection");
+ if(conn->type == CONN_NS) {
+ mhook.rfds.clear();
+ mhook.wfds.clear();
+ logger.putourstatus(msn, mhook.getstatus(), mhook.ourstatus = offline);
+ clist.setoffline(msn);
+ mhook.fonline = false;
+ mhook.slst.clear();
+ face.log(_("+ [msn] disconnected"));
+ face.update();
+ }
+}
+
+void ext_changed_state(msnconn *conn, const char *state) {
+ log("ext_changed_state");
+}
+
+int ext_do_connect_socket(const char *hostname, int port, int ssl) {
+ struct sockaddr_in sa;
+ struct hostent *hp;
+ int a, s;
+ string msgerr = _("+ [msn] cannot connect: ");
+
+ hp = gethostbyname(hostname);
+ if(!hp) {
+ face.log(msgerr + _("could not resolve hostname"));
+ errno = ECONNREFUSED;
+ return -1;
+ }
+
+ memset(&sa, 0, sizeof(sa));
+ memcpy((char *) &sa.sin_addr, hp->h_addr, hp->h_length);
+ sa.sin_family = hp->h_addrtype;
+ sa.sin_port = htons((u_short) port);
+
+ if((s = socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0)
+ return -1;
+
+ if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), ssl) < 0) {
+ face.log(msgerr + _("verify the hostname and port"));
+ close(s);
+ return -1;
+ }
+
+ return s;
+}
+
+int ext_connect_socket_ssl(const char *hostname, int port) {
+ log("ext_connect_socket_ssl");
+ return ext_do_connect_socket(hostname, port, 1);
+}
+
+int ext_connect_socket(const char *hostname, int port) {
+ log("ext_connect_socket");
+ return ext_do_connect_socket(hostname, port, 0);
+}
+
+int ext_server_socket(int port) {
+ log("ext_server_socket");
+ int s;
+ struct sockaddr_in addr;
+
+ if((s = socket(AF_INET, SOCK_STREAM, 0)) < 0)
+ return -1;
+
+ memset(&addr, 0, sizeof(addr));
+ addr.sin_family = AF_INET;
+ addr.sin_port = htons(port);
+
+ if(bind(s, (sockaddr *) &addr, sizeof(addr)) < 0 || listen(s, 1) < 0) {
+ close(s);
+ return -1;
+ }
+
+ return s;
+}
+
+char *ext_get_IP() {
+ log("ext_get_IP");
+ struct hostent *hn;
+ char buf2[1024];
+
+ gethostname(buf2, 1024);
+ hn = gethostbyname(buf2);
+
+ return inet_ntoa(*((struct in_addr*) hn->h_addr));
+}
+
+void ext_protocol_log(const char *buf, int readev, int writeev) {
+ if(readev) {
+ log(string("[IN] ") + buf);
+ } else if(writeev) {
+ log(string("[OUT] ") + buf);
+ }
+}
+
+#endif

View File

@ -0,0 +1,92 @@
--- src/hooks/msnhook.h.orig Mon Nov 3 20:25:39 2003
+++ src/hooks/msnhook.h Mon Nov 3 20:24:23 2003
@@ -0,0 +1,89 @@
+#ifndef __MSNHOOK_H__
+#define __MSNHOOK_H__
+
+#include "abstracthook.h"
+
+#ifdef BUILD_MSN
+
+#include "msn_core.h"
+
+class msnhook : public abstracthook {
+
+ friend void ext_register_sock(int s, int reading, int writing);
+ friend void ext_unregister_sock(int s);
+ friend void ext_new_connection(msnconn *conn);
+ friend void ext_closing_connection(msnconn * conn);
+ friend void ext_buddy_set(msnconn *conn, const char *buddy, const char *friendlyname, const char *status);
+ friend void ext_got_info(msnconn *conn, syncinfo *info);
+ friend void ext_got_friendlyname(msnconn *conn, const char *friendlyname);
+ friend void ext_new_RL_entry(msnconn *conn, const char *username, const char *friendlyname);
+ friend void ext_new_list_entry(msnconn *conn, const char *lst, const char *username);
+ friend void ext_del_list_entry(msnconn *conn, const char *lst, const char *username);
+ friend void ext_got_IM(msnconn *conn, const char *username, const char *friendlyname, message *msg);
+ friend void ext_filetrans_invite(msnconn *conn, const char *username, const char *friendlyname, invitation_ftp *inv);
+ friend void ext_typing_user(msnconn *conn, const char *username, const char *friendlyname);
+ friend void ext_filetrans_progress(invitation_ftp *inv, const char *status, unsigned long sent, unsigned long total);
+ friend void ext_filetrans_failed(invitation_ftp *inv, int error, const char *message);
+ friend void ext_filetrans_success(invitation_ftp *inv);
+
+ protected:
+ imstatus ourstatus;
+ bool fonline, flogged;
+ msnconn conn;
+
+ vector<int> rfds, wfds;
+ map<string, string> friendlynicks;
+ map<string, vector<pair<string, string> > > slst;
+ map<imfile, pair<invitation_ftp *, string> > transferinfo;
+
+ void checkfriendly(icqcontact *c, const string friendlynick,
+ bool forcefetch = false);
+
+ void checkinlist(imcontact ic);
+
+ void removeuser(const imcontact &ic, bool report);
+ bool getfevent(invitation_ftp *fhandle, imfile &fr);
+
+ public:
+ msnhook();
+ ~msnhook();
+
+ void init();
+
+ void connect();
+ void disconnect();
+ void exectimers();
+ void main();
+
+ void getsockets(fd_set &rf, fd_set &wf, fd_set &ef, int &hsocket) const;
+ bool isoursocket(fd_set &rf, fd_set &wf, fd_set &ef) const;
+
+ bool online() const;
+ bool logged() const;
+ bool isconnecting() const;
+ bool enabled() const;
+
+ bool send(const imevent &ev);
+
+ void sendnewuser(const imcontact &c);
+ void removeuser(const imcontact &ic);
+ void requestinfo(const imcontact &ic);
+
+ void sendupdateuserinfo(const icqcontact &c);
+
+ void setautostatus(imstatus st);
+ imstatus getstatus() const;
+
+ void lookup(const imsearchparams &params, verticalmenu &dest);
+ vector<icqcontact *> getneedsync();
+
+ bool knowntransfer(const imfile &fr) const;
+ void replytransfer(const imfile &fr, bool accept, const string &localpath = string());
+ void aborttransfer(const imfile &fr);
+};
+
+extern msnhook mhook;
+
+#endif
+
+#endif

View File

@ -0,0 +1,17 @@
--- src/Makefile.in.orig Sat Oct 25 15:53:46 2003
+++ src/Makefile.in Mon Nov 3 20:16:35 2003
@@ -92,11 +92,11 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl
+INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl -I$(top_srcdir)/blip-0.1
bin_PROGRAMS = centericq
centericq_SOURCES = centericq.cc icqcontact.cc icqgroups.cc eventmanager.cc icqdialogs.cc icqhist.cc imexternal.cc imcontact.cc imlogger.cc accountmanager.cc icqcontacts.cc icqmlist.cc imcontroller.cc icqconf.cc imevents.cc icqface.cc centermain.cc icqgroup.cc
-centericq_LDFLAGS = -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1
-centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@
+centericq_LDFLAGS = -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1 -L$(top_srcdir)/blip-0.1
+centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@ -intl -lblip
SUBDIRS = hooks
EXTRA_DIST = centericq.cc icqcontact.cc icqgroups.cc eventmanager.cc icqdialogs.cc icqhist.cc imexternal.cc imcontact.cc imlogger.cc accountmanager.cc icqcontacts.cc icqmlist.cc imcontroller.cc icqconf.cc imevents.cc icqface.cc centermain.cc icqgroup.cc icqmlist.h imcontroller.h icqcommon.h icqcontacts.h centericq.h icqgroup.h imcontact.h accountmanager.h eventmanager.h imevents.h icqcontact.h imlogger.h icqconf.h icqface.h icqgroups.h icqhist.h imexternal.h
AUTOMAKE_OPTIONS = foreign

View File

@ -0,0 +1,34 @@
--- src/hooks/Makefile.in.orig Sat Oct 25 15:53:46 2003
+++ src/hooks/Makefile.in Mon Nov 3 21:35:39 2003
@@ -92,10 +92,10 @@
USE_NLS = @USE_NLS@
VERSION = @VERSION@
-INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl
+INCLUDES = -I$(top_srcdir)/src -I$(top_srcdir)/src/hooks -I$(top_srcdir)/firetalk-0.1 -I$(top_srcdir)/kkconsui-0.1/include -I$(top_srcdir)/kkstrtext-0.1 -I$(top_srcdir)/libicq2000-0.1 -I$(top_srcdir)/libjabber-0.1 -I$(top_srcdir)/libyahoo2-0.1 -I$(top_srcdir)/kksystr-0.1/include -I$(top_srcdir)/connwrap-0.1 -I$(top_srcdir)/intl -I$(top_srcdir)/blip-0.1
noinst_LIBRARIES = libhooks.a
-libhooks_a_SOURCES = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc
-EXTRA_DIST = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc yahoohook.h aimhook.h jabberhook.h icqhook.h irchook.h abstracthook.h rsshook.h HTTPClient.h ljhook.h
+libhooks_a_SOURCES = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc msnhook.cc
+EXTRA_DIST = yahoohook.cc jabberhook.cc aimhook.cc icqhook.cc irchook.cc abstracthook.cc rsshook.cc HTTPClient.cc ljhook.cc msnhook.cc yahoohook.h aimhook.h jabberhook.h icqhook.h irchook.h abstracthook.h rsshook.h HTTPClient.h ljhook.h msnhook.h
mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
CONFIG_HEADER = ../../config.h
CONFIG_CLEAN_FILES =
@@ -108,7 +108,7 @@
LIBS = @LIBS@
libhooks_a_LIBADD =
libhooks_a_OBJECTS = yahoohook.o jabberhook.o aimhook.o icqhook.o \
-irchook.o abstracthook.o rsshook.o HTTPClient.o ljhook.o
+irchook.o abstracthook.o rsshook.o HTTPClient.o ljhook.o msnhook.o
AR = ar
CXXFLAGS = @CXXFLAGS@
CXXCOMPILE = $(CXX) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS)
@@ -123,7 +123,7 @@
GZIP_ENV = --best
DEP_FILES = .deps/HTTPClient.P .deps/abstracthook.P .deps/aimhook.P \
.deps/icqhook.P .deps/irchook.P .deps/jabberhook.P .deps/ljhook.P \
-.deps/rsshook.P .deps/yahoohook.P
+.deps/rsshook.P .deps/yahoohook.P .deps/msnhook.P
SOURCES = $(libhooks_a_SOURCES)
OBJECTS = $(libhooks_a_OBJECTS)

View File

@ -1,11 +0,0 @@
--- src/icqconf.cc.orig Wed Oct 1 08:27:45 2003
+++ src/icqconf.cc Wed Oct 8 17:28:21 2003
@@ -270,7 +270,7 @@
if(getantispam()) f << "antispam" << endl;
if(getmailcheck()) f << "mailcheck" << endl;
if(getaskaway()) f << "askaway" << endl;
- f << "defcharset" << getdefcharset() << endl;
+ f << "defcharset\t" << getdefcharset() << endl;
param = "";
for(protocolname pname = icq; pname != protocolname_size; (int) pname += 1)

View File

@ -1,28 +0,0 @@
--- blip-0.1/msn_bittybits.C.orig Mon Dec 9 20:31:41 2002
+++ blip-0.1/msn_bittybits.C Thu Oct 23 20:02:19 2003
@@ -18,6 +18,8 @@
char c;
int pos=0, numspaces=0;
+ *numargs = 0;
+
while(1)
{
if(read(sock, &c, 1)<1)
@@ -259,13 +261,16 @@
{
if(*rptr=='\0')
{ *wptr='\0'; break; }
+
if(!(isalpha(*rptr) || isdigit(*rptr)))
{
+ if ( *rptr != '\xc2' && *rptr != '\xb0' ) {
sprintf(wptr, "%%%2x", (int)(*rptr));
rptr++;
wptr+=3;
continue;
+ }
}
*wptr=*rptr;

View File

@ -1,923 +0,0 @@
--- blip-0.1/msn_core.C.orig Sat Dec 14 07:58:01 2002
+++ blip-0.1/msn_core.C Thu Oct 23 20:02:19 2003
@@ -18,19 +18,18 @@
#include <sys/stat.h>
#include "md5.h"
-
#include "msn_core.h"
#include "msn_bittybits.h"
#include "msn_interface.h"
+#include "../connwrap-0.1/connwrap.h"
#define DEBUG 1
+#define MSN_VERSION_ID 0 // ID that is sent after commands like CHG, NLN, etc.
// Define all those extern'ed variables in msn_core.h:
llist * connections=NULL;
-
int next_trid=10;
char buf[BUF_SIZE]; // used for anything temporary
-
char * errors[1000];
char default_error_msg[]="Unknown error code";
@@ -218,143 +217,151 @@
write(conn->sock, buf, strlen(buf));
}
-void msn_sync_lists(msnconn * conn, int version)
+void msn_get_list_info( msnconn *conn, int nargs, char **args )
{
- syncinfo * info=new syncinfo;
+ char buf[ 1000 ];
+ syncinfo *info;
- info->serial=version;
+ info = conn->sync_info;
- sprintf(buf, "SYN %d %d\r\n", next_trid, version);
- write(conn->sock, buf, strlen(buf));
+ if ( NULL == info )
+ {
+ ext_debug("error! : conn->sync_info == NULL in msn_get_list_info");
+ return ;
+ }
- msn_add_callback(conn, msn_syncdata, next_trid, info);
- next_trid++;
-}
+ if ( !nargs )
+ return ;
-void msn_syncdata(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- syncinfo * info=(syncinfo *)data;
-
- if(!strcmp(args[0], "SYN"))
+ if ( !strcmp( args[ 0 ], "SYN" ) )
{
- if(info->serial==atoi(args[2]))
+ if ( info->serial == atoi( args[ 2 ] ) )
{
delete info;
- info=NULL;
- msn_del_callback(conn, trid);
+ info = NULL;
ext_got_info(conn, NULL);
return;
- } else {
- info->serial=atoi(args[2]);
- ext_latest_serial(conn, info->serial);
- msn_add_callback(conn, msn_phonedata, info->serial, info);
}
+
+ info->serial = atoi( args[ 2 ] );
+ ext_latest_serial( conn, info->serial );
+ info->nContacts = atoi( args[ 3 ] );
+ info->nGroups = atoi( args[ 4 ] );
+ return ;
}
- if(!strcmp(args[0], "LST"))
- {
- if(!strcmp(args[2], "FL"))
- {
- if(!strcmp(args[5], "0"))
+ if ( !strcmp( args[ 0 ], "GTC" ) )
{
- info->fl=NULL; info->complete|=LST_FL;
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->fl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_FL; }
- }
+ info->gtc = args[ 1 ][ 0 ];
+ info->complete |= COMPLETE_GTC;
+ ext_got_GTC( conn, args[ 1 ][ 0 ] );
}
- if(!strcmp(args[2], "RL"))
- {
- if(!strcmp(args[5], "0"))
+
+ if ( !strcmp( args[ 0 ], "BLP" ) )
{
- info->rl=NULL; info->complete|=LST_RL; // no mates! :-)
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->rl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_RL; }
+ info->blp = args[ 1 ][0];
+ info->complete |= COMPLETE_BLP;
+ ext_got_BLP( conn, args[ 1 ][ 0 ] );
}
+
+ if ( !strcmp( args[ 0 ], "PRP" ) )
+ {
+ // We just eat PRP-codes.
+ return ;
}
- if(!strcmp(args[2], "AL"))
+
+ if ( !strcmp( args[ 0 ], "LSG" ) )
{
- if(!strcmp(args[5], "0"))
+ if ( !info->nContacts )
{
- info->al=NULL; info->complete|=LST_AL;
- } else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->al, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_AL; }
+ msn_check_rl(conn, info);
+ ext_got_info(conn, info);
+ delete info;
+ conn->sync = 0;
}
+
+ // Just eat 'm.
+ return ;
}
- if(!strcmp(args[2], "BL"))
- {
- if(!strcmp(args[5], "0"))
+
+ if ( !strcmp( args[ 0 ], "BPR" ) )
{
- info->bl=NULL; info->complete|=LST_BL;
+ if ( !info->nFound ) {
+ ext_debug("MSNp8: error: got BPR without contact");
} else {
- userdata * newuser=new userdata();
- newuser->username=msn_permstring(args[6]);
- newuser->friendlyname=msn_decode_URL(msn_permstring(args[6]));
- msn_add_to_llist(info->bl, newuser);
- if(atoi(args[4])==atoi(args[5]))
- { info->complete|=LST_BL; }
+ llist *ll = info->fl;
+
+ while( ll ) {
+ userdata * ud = (userdata *) ll->data;
+
+ if( !strcmp( ud->username, info->last_user_handled ) )
+ {
+ phonedata * newphone=new phonedata();
+ newphone->title=msn_permstring(args[1]);
+ newphone->number=msn_decode_URL(msn_permstring(args[2]));
+ msn_add_to_llist( ud->phone, newphone );
+ break;
}
+
+ ll = ll->next;
}
}
- if(!strcmp(args[0], "GTC"))
- {
- info->gtc=args[3][0];
- info->complete|=COMPLETE_GTC;
- ext_got_GTC(conn, args[3][0]);
+ return ;
}
- if(!strcmp(args[0], "BLP"))
+ // 0 1 2
+ // LST email@address.com Friendly%20Nickname w x,y,z
+ if ( !strcmp( args[ 0 ], "LST" ) )
{
- info->blp=args[3][0];
- info->complete|=COMPLETE_BLP;
- ext_got_BLP(conn, args[3][0]);
- }
+ // XXX - Todo: see if the user is really on our FL
+ // list and handle the BL list.
+
+ userdata *newuser_fl = new userdata();
+ newuser_fl->username = msn_permstring( args[ 1 ] );
+ newuser_fl->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ info->last_user_handled = newuser_fl->username;
+
+ msn_add_to_llist( info->fl, newuser_fl );
+
+ userdata *newuser_rl = new userdata();
+ newuser_rl->username = msn_permstring( args[ 1 ] );
+ newuser_rl->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ msn_add_to_llist( info->rl, newuser_rl );
- if(info->complete == (LST_FL|LST_RL|LST_AL|LST_BL|COMPLETE_BLP|COMPLETE_GTC))
+ userdata *newuser_al = new userdata();
+ newuser_al->username = msn_permstring( args[ 1 ] );
+ newuser_al->friendlyname = msn_decode_URL( msn_permstring( args[ 1 ] ) );
+
+ msn_add_to_llist( info->al, newuser_al );
+
+ info->nFound++;
+
+ if ( info->nFound == info->nContacts )
{
- msn_del_callback(conn, trid);
- msn_del_callback(conn, info->serial);
msn_check_rl(conn, info);
ext_got_info(conn, info);
delete info;
+ conn->sync = 0;
+ }
}
}
-void msn_phonedata(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
+void msn_sync_lists(msnconn * conn, int version)
{
- syncinfo * info=(syncinfo *)data;
+ syncinfo * info=new syncinfo;
- if(!strcmp(args[0], "BPR"))
- {
- llist * ll = info->fl;
- while(ll) {
- userdata * ud = (userdata *) ll->data;
- if(!strcmp(ud->username, args[2]))
- {
- phonedata * newphone=new phonedata();
- newphone->title=msn_permstring(args[3]);
- newphone->number=msn_decode_URL(msn_permstring(args[4]));
- msn_add_to_llist(ud->phone, newphone);
- break;
- }
- ll = ll->next;
- }
- }
+ info->serial=version;
+
+ sprintf(buf, "SYN %d %d\r\n", next_trid, version);
+ write(conn->sock, buf, strlen(buf));
+
+ conn->sync = 1;
+ conn->sync_info = info;
+
+ next_trid++;
}
void msn_check_rl(msnconn * conn, syncinfo * info)
@@ -544,6 +551,11 @@
if(!readable) { return; }
args=msn_read_line(sock, &numargs);
+ if ( !numargs )
+ {
+ ext_debug("msn: error: no arguments for this data");
+ return ;
+ }
if(args==NULL)
{
@@ -582,6 +594,22 @@
trid=atoi(args[1]);
+ if ( conn->sync )
+ {
+ // connection is synching. is this a SYNC-relation instruction?
+ if ( !strcmp( args[ 0 ], "SYN" ) || !strcmp( args[ 0 ], "GTC") || !strcmp( args[ 0 ], "BLP" ) ||
+ !strcmp( args[ 0 ], "PRP" ) || !strcmp( args[ 0 ], "LSG") || !strcmp( args[ 0 ], "BPR" ) ||
+ !strcmp( args[ 0 ], "LST" ) )
+ {
+ msn_get_list_info( conn, numargs, args );
+ delete args[0];
+ delete args;
+ return ;
+ }
+
+ // else: it's a normal message
+ }
+
list=conn->callbacks;
if(list!=NULL && trid>0)
@@ -775,6 +803,10 @@
#endif
if((tmp=strstr(content, "; charset"))!=NULL) { *tmp='\0'; }
+ if(!strcmp(content, "text/x-msmsgsprofile"))
+ {
+ ext_debug("MSNp8: got x-msmsgsprofile");
+ } else
if(!strcmp(content, "text/plain"))
{
message * msg=new message;
@@ -1024,7 +1056,6 @@
write(conn->sock, "VER MSNFTP\r\n", strlen("VER MSNFTP\r\n"));
}
-
void msn_handle_filetrans_incoming(msnconn * conn, int readable, int writable)
{
authdata_FTP * auth=(authdata_FTP *)conn->auth;
@@ -1445,10 +1476,12 @@
md5_init(&state);
md5_append(&state, (md5_byte_t *)(args[2]), strlen(args[2]));
- md5_append(&state, (md5_byte_t *)"Q1P7W2E4J9R8U3S5", 16);
+ md5_append(&state, (md5_byte_t *)"VT6PX?UQTM4WM%YR", 16);
+
md5_finish(&state, digest);
- sprintf(buf, "QRY %d msmsgs@msnmsgr.com 32\r\n", next_trid++);
+ sprintf(buf, "QRY %d PROD0038W!61ZTF9 32\r\n", next_trid++ );
+
write(conn->sock, buf, strlen(buf));
for(a=0; a<16; a++)
@@ -1591,8 +1624,426 @@
return inv;
}
+#define szUser info->username
+#define szPassword info->password
+
+int msn_login_read( int nSock, char *buf, int nMax )
+{
+ return cw_read( nSock, buf, nMax, 0 );
+}
+
+int msn_login_wait( int nSocket, char *szCommand )
+{
+ int nRet = 0;
+
+ while ( !nRet )
+ nRet = read( nSocket, szCommand, 1000 );
+
+ #ifdef MSNDEBUG
+ printf("<< %s", szCommand );
+ #endif
+
+ return 1;
+}
+
+void msn_login_write1( int nSocket, char *szString, char *szArg )
+{
+ char szWrite[ 1000 ];
+
+ // ext_debug( szString );
+ // ext_debug( szArg );
+
+ memset( szWrite, 0, 999 );
+ sprintf( szWrite, "%s %s\r\n", szString, szArg );
+
+ // ext_debug( szWrite );
+
+ cw_write( nSocket, szWrite, strlen( szWrite ), 0 );
+}
+
+void msn_login_write( int nSocket, char *szString )
+{
+ char szWrite[ 1000 ];
+
+ memset( szWrite, 0, 1000 );
+ sprintf( szWrite, "%s\r\n", szString );
+
+ cw_write( nSocket, szWrite, strlen( szWrite ), 0 );
+}
+
+int msn_login_connect( int nPort, char *szAddress )
+{
+ return ext_connect_socket( szAddress, nPort );
+}
+
+int msn_login_ssl_write( int nSock, char *str )
+{
+ return cw_write( nSock, str, strlen( str ), 1 );
+}
+
+int msn_login_ssl_read( int nSock, char *buf, int nMax )
+{
+ return cw_read( nSock, buf, nMax, 1 );
+}
+
+int msn_login_close( int nSock )
+{
+ return cw_close( nSock );
+}
+
+int msn_login_ssl_connect( int nPort, char *szAddr )
+{
+ return ext_connect_socket_ssl( szAddr, nPort );
+}
+
+int msn_login_get_server( char *str, char *filter, char *Server, char *Site )
+{
+ char *c, *c1, *c2;
+
+ c = strstr( str, filter );
+ if ( NULL == c )
+ return 0;
+ // Skip the "Filter="-part.
+ c++;
+ c += strlen( filter );
+ c1 = strchr( c, '/' );
+ if ( NULL == c1 )
+ return 0;
+ c2 = strchr( c1, ',' );
+ if ( NULL == c2 )
+ return 0;
+
+ strncpy( Server, c, (unsigned long)c1 - (unsigned long)c );
+ strncpy( Site, c1, (unsigned long)c2 - (unsigned long)c1 );
+
+ return 1;
+}
+
+int msnAuth( char *lc, char *ticket, char *user, char *password )
+{
+ int nexus; // Passport Login Nexus
+ int logins; // Login Server
+ char result[ 5000 ];
+ char result2[ 1000 ];
+ char Server[ 100 ]; // e.g. www.server.com
+ char Site[ 100 ]; // e.g. /site.html
+ char String[ 800 ];
+ int i;
+ char mail[ 255 ];
+ char name[ 255 ];
+
+ memset( mail, 0, 255 );
+ memset( name, 0, 255 );
+
+ for ( i = 0; i < strlen( user ); i++ )
+ {
+ if ( user[i] == '@' )
+ {
+ strncpy( name, user, i );
+ strcpy( mail, (char*)( (unsigned long)user + i + 1 ) );
+ break;
+ }
+ }
+
+ memset( Server, 0, 100 );
+ memset( Site, 0, 100 );
+
+ nexus = msn_login_ssl_connect( 443, "nexus.passport.com" );
+ msn_login_ssl_write( nexus, "GET /rdr/pprdr.asp HTTP/1.0\r\n\r\n" );
+ msn_login_ssl_read( nexus, result, 800 );
+ msn_login_close( nexus );
+ msn_login_get_server( result, "DALogin", Server, Site );
+
+ #ifdef MSNDEBUG
+ printf("Connecting to server '%s' .. site '%s'\n", Server, Site );
+ #endif
+
+ for ( ; ; )
+ {
+ // Connect to Login Server
+ logins = msn_login_ssl_connect( 443, Server );
+ memset( String, 0, 800 );
+ sprintf( String, "GET %s HTTP/1.1\r\n"
+ "Authorization: Passport1.4 OrgVerb=GET,OrgURL=http%%3A%%2F%%2Fmessenger%%2Emsn%%2Ecom,sign-in=%s%%40%s,pwd=%s,%s\r\n"
+ "Host: %s\r\n\r\n",
+ Site, name, mail, password, lc, Server );
+
+ #ifdef MSNDEBUG
+ printf("Writing: \n%s\n", String );
+ #endif
+
+ msn_login_ssl_write( logins, String );
+
+ memset( result, 0, 5000 );
+ memset( result2, 0, 1000 );
+
+ msn_login_ssl_read( logins, result, 5000 );
+ msn_login_ssl_read( logins, result2, 1000 );
+
+ strcat( result, result2 );
+
+ if ( strstr( result, "200 OK" ) )
+ {
+ char *tick;
+ char *c3, *c4;
+ // Okay.
+
+ tick = strstr( result, "t=" );
+ if ( NULL == tick )
+ {
+ #ifdef MSNDEBUG
+ printf("No t= found in response.\n");
+ #endif
+ return 0;
+ }
+
+ tick += 2;
+
+ c4 = strstr( tick, "," );
+
+ strncpy( ticket, tick, (unsigned long)c4 - (unsigned long)tick - 1 );
+
+ //msn_login_close( logins );
+ return 1;
+ }
+
+ if ( strstr( result, "302 Found") && strstr( result, "redir" ) && strstr( result, "Location: " ) )
+ {
+ // Redirection.
+ char *c3, *c4;
+
+ c3 = strstr( result, "Location: " );
+ c3 += 10;
+
+ c3 = strstr( c3, "https://" );
+ c3 += 8;
+
+ c4 = strstr( c3, "/" );
+ strncpy( Server, c3, (unsigned long)c4 - (unsigned long)c3 );
+ strncpy( Site, c4, (unsigned long)strchr( c4, '\r' ) - (unsigned long)c4 );
+
+ // printf("Redirection to server [%s] - Site [%s]\n", Server, Site );
+ msn_login_close( logins );
+ continue;
+ }
+
+ break;
+ }
+
+ // printf("Error\n");
+ return 0;
+}
+
+int msn_connect_v8_error( connectinfo *info, msnconn *conn, char *szErr )
+{
+ ext_show_error( NULL, szErr );
+ delete info;
+
+ if ( conn->sock != -1 )
+ {
+ ext_unregister_sock( conn->sock );
+ close( conn->sock );
+ conn->sock = -1;
+ }
+
+ return -1;
+}
+
+int msn_connect_v8( connectinfo *info, msnconn *conn, int *nNextTrid )
+{
+ int ds; // Dispatch Server
+ char result[ 1000 ];
+ char *c;
+ char szIp[ 20 ];
+ char szPort[ 20 ];
+ int nPort;
+ char lc[ 400 ];
+ char ticket[ 2000 ];
+
+ memset( result, 0, 500 );
+
+ ext_debug("MSNp8: finding login server");
+
+ // ds = msn_login_connect( 1863, "messenger.hotmail.com" );
+ ds = conn->sock;
+
+ // >> VER 1 MSNP8 CVR0\r\n
+ msn_login_write( ds, "VER 1 MSNP8 CVR0" );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "VER 1" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive VER 1)" );
+
+ // >> CVR 2 0x0409 win 4.10 i386 MSNMSGR 5.0.0544 MSMSGS something@something.com\r\n
+ // ext_debug( szUser );
+
+ msn_login_write1( ds, "CVR 2 0x0409 winnt 5.1 i386 MSNMSGR 5.0.0540 MSMSGS", szUser );
+
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "CVR 2" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive CVR 2)" );
+
+ // >> USR 3 TWN I something@something.com\r\n
+ msn_login_write1( ds, "USR 3 TWN I", szUser );
+ msn_login_wait( ds, result );
+ if ( !strstr( result, "XFR 3 NS " ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive XFR 3)" );
+
+ // Read MSN Server IP from message.
+ c = strstr( result, "NS ");
+ c += 3;
+ memset( szIp, 0, 20 );
+ memset( szPort, 0, 20 );
+ strncpy( szIp, c, (unsigned long)strchr( c, ':' ) - (unsigned long)c );
+ c = strchr( c, ':' ); c++;
+ strncpy( szPort, c, (unsigned long)strchr( c, ' ' ) - (unsigned long)c );
+ nPort = atoi( szPort );
+
+ // Close current socket.
+ msn_login_close( ds );
+ ext_unregister_sock( ds );
+ conn->sock = -1;
+
+ #ifdef MSNDEBUG
+ printf("* Connecting to IP `%s' port %d *\n", szIp, nPort );
+ #endif
+
+ ext_debug("MSNp8: found.. connecting");
+
+ // Try to connect to other server.
+ ds = msn_login_connect( nPort, szIp );
+ if ( ds <= 0 )
+ return msn_connect_v8_error( info, conn, "Error connecting to specified MSN Server" );
+
+ // OK. Register the socket.
+ conn->sock = ds;
+ ext_register_sock( ds, 1, 0 );
+
+ // >> VER 4 MSNP8 CVR0\r\n
+ msn_login_write( ds, "VER 4 MSNP8 CVR0" );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "VER 4" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive VER 4)" );
+
+ // >> CVR 5 0x0409 win 4.10 i386 MSNMSGR 5.0.0544 MSMSGS something@something.com\r\n
+ msn_login_write1( ds, "CVR 5 0x0409 winnt 5.1 i386 MSNMSGR 5.0.0540 MSMSGS", szUser );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "CVR 5" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive CVR 5)" );
+
+ // >> USR 6 TWN I something@something.com\r\n
+ msn_login_write1( ds, "USR 6 TWN I", szUser );
+ msn_login_wait( ds, result );
+
+ // << USR 6 TWN S something@something.com lc=....,....=...\r\n
+ if ( !strstr( result, "TWN S" ) )
+ return msn_connect_v8_error( info, conn, "Protocol error (didn't receive TWS S)" );
+
+ memset( lc, 0, 400 );
+ c = strstr( result, "TWN S " );
+ c+=6;
+
+ strncpy( lc, c, (unsigned long)strchr(c, '\r') - (unsigned long)c );
+
+ #ifdef MSNDEBUG
+ printf("LC-etc string = `%s'\n", lc );
+ #endif
+
+ memset( ticket, 0, 2000 );
+
+ ext_debug("MSNp8: doing SSL auth");
+
+ if ( ! msnAuth( lc, ticket, szUser, szPassword ) )
+ {
+ // printf("Error #6\n");
+ return 0;
+ }
+
+ ext_debug("MSNp8: OK.. logging in");
+
+ #ifdef MSNDEBUG
+ printf("Ticket = `%s'\n", ticket );
+ #endif
+
+ memset( result, 0, 500 );
+ sprintf( result, "USR 7 TWN S t=%s", ticket );
+
+ // >> USR 7 TWN S t=<ticket>
+ msn_login_write( ds, result );
+ memset( result, 0, 500 );
+ msn_login_wait( ds, result );
+
+ if ( !strstr( result, "USR 7 OK") )
+ {
+ if ( result[ 0 ] >= '0' && result[ 0 ] <= '9' )
+ {
+ char *err;
+ int nCode = 0;
+ // We received an error code.
+
+ err = strchr( result, ' ' );
+ if ( NULL == err )
+ nCode = atoi( result );
+ else {
+ *err = '\0';
+ nCode = atoi( result );
+ }
+ if ( nCode <= 0 )
+ return msn_connect_v8_error( info, conn, "Protocol error (Invalid response after USR 7)" );
+ return nCode;
+ }
+
+ // Invalid response.
+ return msn_connect_v8_error( info, conn, "Protocol error (Invalid response after USR 7)" );
+ }
+
+ // We are now connected to the MSN Server
+
+ // msn_login_write( ds, "OUT" );
+ // msn_login_close( ds );
+
+ // << USR 7 OK something@something.com Something%20Friendly%Nick 1 0
+ {
+ char *szFriendly;
+ char *cEnd;
+ int i;
+
+ szFriendly = result;
+
+ for ( i = 0; i < 4; i++ )
+ {
+ szFriendly = strchr( szFriendly, ' ' );
+
+ if ( NULL == szFriendly )
+ {
+ ext_got_friendlyname( conn, "Unknown nickname" );
+ return 0;
+ }
+
+ szFriendly++;
+ }
+
+ cEnd = strchr( szFriendly, ' ');
+ if ( NULL != cEnd )
+ *cEnd = '\0';
+
+ // ext_debug( msn_decode_URL( szFriendly ) );
+ ext_got_friendlyname( conn, msn_decode_URL( szFriendly ) );
+ }
+
+ *nNextTrid = 8;
+
+ // No error.
+ return 0;
+}
+
void msn_connect(msnconn * conn, const char * server, int port)
{
+ int result;
+
conn->ready=0;
if(conn->type==CONN_SB)
@@ -1645,106 +2096,37 @@
ext_register_sock(conn->sock, 1, 0);
- #ifdef MSNDEBUG
- printf("Connected\n"); // DEBUG
- #endif
-
- sprintf(buf, "VER %d MSNP7\r\n", next_trid);
- write(conn->sock, buf, strlen(buf));
- msn_add_callback(conn, msn_connect_2, next_trid, (callback_data *)info);
- next_trid++;
-}
-
-// Further connection functions:
+ // Okay, now try to connect.
-void msn_connect_2(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
+ ext_debug("MSNp8: connecting to MSN.. this could take a few seconds");
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
+ result = msn_connect_v8( info, conn, &next_trid );
- if(strcmp(args[0], "VER") || strcmp(args[2], "MSNP7")) // if either *differs*...
+ if ( 0 != result )
{
- ext_show_error(NULL, "Protocol negotiation failed");
- delete info;
- ext_unregister_sock(conn->sock);
- close(conn->sock);
- conn->sock=-1;
- return;
- }
-
- sprintf(buf, "USR %d MD5 I %s\r\n", next_trid, info->username);
- write(conn->sock, buf, strlen(buf));
-
- msn_add_callback(conn, msn_connect_3, next_trid, data);
- next_trid++;
-}
-
-void msn_connect_3(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- md5_state_t state;
- md5_byte_t digest[16];
- int a;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
+ // Error code.
- if(isdigit(args[0][0]))
+ if ( result > 0 )
{
- msn_show_verbose_error(conn, atoi(args[0]));
- msn_clean_up(conn);
+ msn_show_verbose_error( conn, result );
delete info;
- return;
- }
+ msn_clean_up( conn );
+ conn->sock = -1;
- // OK, the challenge just arrived as args[4]
+ } // else: connection failed completely. msn_connect_v8 already took care of destroying the connection
- md5_init(&state);
- md5_append(&state, (md5_byte_t *)(args[4]), strlen(args[4]));
- md5_append(&state, (md5_byte_t *)(info->password), strlen(info->password));
- md5_finish(&state, digest);
-
- sprintf(buf, "USR %d MD5 S ", next_trid);
- write(conn->sock, buf, strlen(buf));
-
- for(a=0; a<16; a++)
- {
- sprintf(buf, "%02x", digest[a]);
- write(conn->sock, buf, 2);
}
-
- write(conn->sock, "\r\n", 2);
-
- msn_add_callback(conn, msn_connect_4, next_trid, data);
- next_trid++;
-}
-
-void msn_connect_4(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
-
- if(isdigit(args[0][0]))
+ else
{
- msn_show_verbose_error(conn, atoi(args[0]));
- delete info;
- msn_clean_up(conn);
- return;
- }
-
- ext_got_friendlyname(conn, msn_decode_URL(args[4]));
+ // We received no error code. Everything went ok!
delete info;
- next_trid++;
+ ext_debug("MSNp8: OK");
- conn->ready=1;
- ext_new_connection(conn);
+ conn->ready = 1;
+ ext_new_connection( conn );
+ }
}
void msn_SB_ans(msnconn * conn, int trid, char ** args, int numargs, callback_data * data)
@@ -1774,30 +2156,7 @@
void msn_set_state(msnconn * conn, const char * state)
{
- sprintf(buf, "CHG %d %s\r\n", next_trid, state);
+ sprintf(buf, "CHG %d %s %d\r\n", next_trid, state, MSN_VERSION_ID );
write(conn->sock, buf, strlen(buf));
next_trid++;
}
-
-/*
-void msn_connect_3(msnconn * conn, char ** args, int numargs, callback_data * data)
-{
- connectinfo * info;
-
- info=(connectinfo *)data;
- msn_del_callback(conn, trid);
- trid++;
-
- if(isdigit(args[0][0]))
- {
- msn_print_verbose_error(conn, atoi(args[0]));
- delete info;
- return;
- }
-
- sprintf(buf, "INF %d\r\n", trid, info->username);
- write(conn.sock, buf, strlen(buf));
-
- msn_add_callback(conn, msn_connect_4, trid, data);
-}
-*/

View File

@ -1,123 +0,0 @@
--- blip-0.1/msn_core.h.orig Sat Dec 14 07:58:06 2002
+++ blip-0.1/msn_core.h Thu Oct 23 20:02:19 2003
@@ -24,6 +24,49 @@
~char_data() { if(c!=NULL) { delete c; } }
};
+class callback_data
+{};
+
+class callback : public llist_data
+{
+ public:
+ int trid;
+ void (*func)(struct msnconn * conn, int trid, char ** args, int numargs, callback_data * data);
+ callback_data * data; // just gets passed
+};
+
+// Intermediate steps in synchronisation
+class syncinfo : public callback_data
+{
+ public:
+
+ llist * fl;
+ llist * rl;
+ llist * al;
+ llist * bl;
+
+ unsigned int complete;
+
+ int serial;
+ int nContacts;
+ int nGroups;
+ int nFound;
+
+ char *last_user_handled;
+
+ char blp;
+ char gtc;
+
+ syncinfo() { nFound = 0; nContacts = 0; blp='A'; gtc='A'; fl=rl=al=bl=NULL; complete=0; serial=0; }
+ ~syncinfo()
+ {
+ if(fl!=NULL) { delete fl; }
+ if(rl!=NULL) { delete rl; }
+ if(al!=NULL) { delete al; }
+ if(bl!=NULL) { delete bl; }
+ }
+};
+
class message : public llist_data // This class encapsulates all that you need to know (tm) about a MSG
{
public:
@@ -81,14 +124,17 @@
public:
int sock; // Socket (durr...)
int type; // one of the #defines below
+ int sync; // syncing
int ready;
+
+ syncinfo *sync_info;
llist * users; // Users in this session - only for SB connections
llist * invitations_out; // invitations extended but not responded to
llist * invitations_in; // invitations received but not responded to
llist * callbacks;
authdata * auth;
- msnconn() { users=NULL; callbacks=NULL; invitations_out=NULL; invitations_in=NULL; }
+ msnconn() { sync = 0; users=NULL; callbacks=NULL; invitations_out=NULL; invitations_in=NULL; }
~msnconn()
{
if(users!=NULL) { delete users; }
@@ -177,17 +223,6 @@
#define MSNFTP_SEND 1
#define MSNFTP_RECV 2
-class callback_data
-{};
-
-class callback : public llist_data
-{
- public:
- int trid;
- void (*func)(struct msnconn * conn, int trid, char ** args, int numargs, callback_data * data);
- callback_data * data; // just gets passed
-};
-
extern llist * connections;
extern int next_trid;
@@ -224,33 +259,6 @@
#define COMPLETE_BLP 16
#define COMPLETE_GTC 32
-
-// Intermediate steps in synchronisation
-class syncinfo : public callback_data
-{
- public:
-
- llist * fl;
- llist * rl;
- llist * al;
- llist * bl;
-
- unsigned int complete;
-
- int serial;
-
- char blp;
- char gtc;
-
- syncinfo() { blp='A'; gtc='A'; fl=rl=al=bl=NULL; complete=0; serial=0; }
- ~syncinfo()
- {
- if(fl!=NULL) { delete fl; }
- if(rl!=NULL) { delete rl; }
- if(al!=NULL) { delete al; }
- if(bl!=NULL) { delete bl; }
- }
-};
void msn_set_friendlyname(msnconn * conn, const char * friendlyname);

View File

@ -1,20 +0,0 @@
--- blip-0.1/msn_interface.h.orig Mon Dec 9 20:31:41 2002
+++ blip-0.1/msn_interface.h Thu Oct 23 20:02:19 2003
@@ -25,6 +25,8 @@
void ext_got_info(msnconn * conn, syncinfo * data);
+void ext_debug( char *msg );
+
void ext_latest_serial(msnconn * conn, int serial);
void ext_got_GTC(msnconn * conn, char c);
@@ -78,6 +80,8 @@
Return: Nothing
*/
int ext_connect_socket(const char * server, int port);
+
+int ext_connect_socket_ssl(const char * server, int port);
int ext_server_socket(int port);

View File

@ -1,98 +0,0 @@
--- src/hooks/msnhook.cc.orig Tue Sep 30 19:38:43 2003
+++ src/hooks/msnhook.cc Thu Oct 23 20:12:58 2003
@@ -120,11 +120,14 @@
face.log(_("+ [msn] connecting to the server"));
+ flogged = false;
+ fonline = true;
+
msn_init(&conn, nicknormalize(account.nickname).c_str(), account.password.c_str());
msn_connect(&conn, account.server.c_str(), account.port);
fonline = true;
- flogged = false;
+ flogged = true;
}
void msnhook::disconnect() {
@@ -248,7 +251,7 @@
}
icqcontact *c = clist.get(ev.getcontact());
- text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf8");
+ text = siconv(text, conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset(), "utf-8");
if(c)
if(c->getstatus() != offline || !c->inlist()) {
@@ -378,11 +381,11 @@
void msnhook::checkfriendly(icqcontact *c, const string friendlynick, bool forcefetch) {
string oldnick = c->getnick();
- string newnick = unmime(friendlynick);
+ string newnick = siconv(unmime(friendlynick), "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
c->setnick(newnick);
- if(forcefetch || (oldnick != newnick && c->getdispnick() == oldnick) || oldnick.empty()) {
+ if(forcefetch || (oldnick != newnick && c->getdispnick() != oldnick) || oldnick.empty()) {
c->setdispnick(newnick);
face.relaxedupdate();
}
@@ -450,6 +453,12 @@
#endif
}
+int ext_debug( char *str )
+{
+ log( str );
+ return 0;
+}
+
void ext_register_sock(int s, int reading, int writing) {
log("ext_register_sock");
if(reading) mhook.rfds.push_back(s);
@@ -602,7 +611,7 @@
mhook.checkinlist(ic);
- string text = siconv(msg->body, "utf8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
+ string text = siconv(msg->body, "utf-8", conf.getrussian(msn) ? "koi8-u" : conf.getdefcharset());
em.store(immessage(ic, imevent::incoming, text));
}
@@ -710,8 +719,7 @@
log("ext_changed_state");
}
-int ext_connect_socket(const char *hostname, int port) {
- log("ext_connect_socket");
+int ext_do_connect_socket(const char *hostname, int port, int ssl) {
struct sockaddr_in sa;
struct hostent *hp;
int a, s;
@@ -732,13 +740,23 @@
if((s = socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0)
return -1;
- if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), 0) < 0) {
+ if(cw_connect(s, (struct sockaddr *) &sa, sizeof(sa), ssl) < 0) {
face.log(msgerr + _("verify the hostname and port"));
close(s);
return -1;
}
return s;
+}
+
+int ext_connect_socket_ssl(const char *hostname, int port) {
+ log("ext_connect_socket_ssl");
+ return ext_do_connect_socket(hostname, port, 1);
+}
+
+int ext_connect_socket(const char *hostname, int port) {
+ log("ext_connect_socket");
+ return ext_do_connect_socket(hostname, port, 0);
}
int ext_server_socket(int port) {

View File

@ -1,7 +0,0 @@
--- src/Makefile.in.orig Thu May 8 14:58:44 2003
+++ src/Makefile.in Thu May 8 14:58:57 2003
@@ -98,3 +98,3 @@
centericq_LDFLAGS = -L$(top_srcdir)/blip-0.1 -L$(top_srcdir)/firetalk-0.1 -L$(top_srcdir)/kkconsui-0.1 -L$(top_srcdir)/kkstrtext-0.1 -L$(top_srcdir)/libicq2000-0.1 -L$(top_srcdir)/libjabber-0.1 -L$(top_srcdir)/libyahoo2-0.1 -L$(top_srcdir)/kksystr-0.1 -L$(top_srcdir)/connwrap-0.1
-centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lblip -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@
+centericq_LDADD = $(top_srcdir)/src/hooks/libhooks.a -lblip -lfiretalk -lkkconsui -lkkstrtext -llibicq2000 -llibjabber -llibyahoo2 -lkksystr -lconnwrap @INTLLIBS@ -lintl
SUBDIRS = hooks

View File

@ -1,11 +0,0 @@
--- src/hooks/yahoohook.cc.orig Fri Oct 3 03:55:06 2003
+++ src/hooks/yahoohook.cc Wed Oct 8 17:29:21 2003
@@ -556,7 +556,7 @@
string yahoohook::decode(const string &text, bool utf) {
if(utf)
- return siconv(text, "utf8",
+ return siconv(text, "utf-8",
conf.getrussian(proto) ? "koi8-u" : conf.getdefcharset());
return rushtmlconv("wk", text);

View File

@ -1,5 +1,5 @@
Centericq is a text mode menu- and window-driven IM interface that
supports the ICQ2000, Yahoo!, AIM, MSN and IRC protocols. It allows you
supports the ICQ2000, Yahoo!, AIM, and IRC protocols. It allows you
to send, receive, and forward messages, URLs, SMSes, contacts, and email
express messages. It also lets you set your own and fetch others' away
messages, and define external handlers for incoming events. You can
@ -11,4 +11,6 @@ inactivity, and have your own ignore, visible, and invisible lists.
It can also associate events with sounds, make log of events, and
allows arrangement of contacts into groups.
Note: MSN protocol is not supported offcially.
WWW: http://konst.org.ua/centericq/