Robert Lowry avatar Robert Lowry committed ec208bd

first commit.

Comments (0)

Files changed (6)

+MIT/X Consortium License
+
+(C)opyright MMX Robert Lowry <robertwlowry@gmail.com>
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the "Software"),
+to deal in the Software without restriction, including without limitation
+the rights to use, copy, modify, merge, publish, distribute, sublicense,
+and/or sell copies of the Software, and to permit persons to whom the
+Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+DEALINGS IN THE SOFTWARE.
+
+# ircsrv - minimalist irc client server
+
+include config.mk
+
+SRC = ircsrv.c
+OBJ = ${SRC:.c=.o}
+BIN = ${OBJ:.o=}
+
+all: options ${BIN}
+
+options:
+	@echo ircsrv build options:
+	@echo "CFLAGS	= ${CFLAGS}"
+	@echo "LDFLAGS	= ${LDFLAGS}"
+	@echo "CC	= ${CC}"
+
+.c.o:
+	@echo CC $<
+	@${CC} -c ${CFLAGS} $<
+
+.o:
+	@echo CC -o $@
+	@${CC} -o $@ $< ${LDFLAGS}
+
+${OBJ}: config.mk
+
+clean:
+	@echo cleaning
+	@rm -f ${BIN} ${OBJ} ircsrv-${VERSION}.tar.gz 
+
+dist: clean
+	@echo creating ircsrv-${VERSION}.tar.gz
+	@mkdir -p ircsrv-${VERSION}
+	@cp -r LICENSE Makefile README config.mk ircsrv.1 ircsrv-${VERSION}
+	@tar -cf ircsrv-${VERSION}.tar ircsrv-${VERSION}
+	@gzip ircsrv-${VERSION}.tar
+	@rm -rf ircsrv-${VERSION}
+
+install: all
+	@echo installing executable files to ${DESTDIR}${PREFIX}/bin
+	@mkdir -p ${DESTDIR}${PREFIX}/bin
+	@for bin in ${BIN}; do cp -f $$bin ${DESTDIR}${PREFIX}/bin/$$bin; done
+	@for bin in ${BIN}; do chmod 755   ${DESTDIR}${PREFIX}/bin/$$bin; done
+	@echo installing man pages to ${DESTDIR}${MANPREFIX}/man1
+	@mkdir -p ${DESTDIR}${MANPREFIX}/man1
+	@sed "s/VERSION/${VERSION}/g" < ircsrv.1 > ${DESTDIR}${MANPREFIX}/man1/ircsrv.1
+	@chmod 644 ${DESTDIR}${MANPREFIX}/man1/ircsrv.1
+
+uninstall:
+	@echo removing executable friles from ${DESTDIR}${PREFIX}/bin
+	@for bin in ${BIN}; do rm -f ${DESTDIR}${PREFIX}/bin/$$bin; done
+	@echo removing man pages from ${DESTDIR}${MANPREFIX}/man1
+	@rm -rf ${DESTDIR}${MANPREFIX}/man1/ircsrv.1
+
+.PHONY: all options clean dist install uninstall
+nii - ncurses ii interface
+--------------------------
+ircsrv is a minimalist passive irc client. It opens a connection to an IRC
+server and simply maintains that connection (by responding to PINGs and 
+reconnecting when necessary) while providing an interface for access to the
+raw IRC protocol. The idea is to provide a simple way for commandline tools to
+access IRC while staying as minimal as possible.
+
+Installation
+------------
+Edit config.mk to match your local machine's configuration. ircsrv is
+installed to /usr/local by default.
+
+Then enter the following commands to build and install:
+
+$ make 
+
+then:
+
+$ make install
+
+(as root if necessary)
+
+Running ircsrv
+--------------
+Simply invoke the 'ircsrv' command with the required arguments.
+# ircsrv version
+VERSION	= 0.1
+
+# paths
+PREFIX = /usr/local
+MANPREFIX = ${PREFIX}/share/man
+
+# includes and libs
+INCS = -I. -I/usr/include
+LIBS = -L/usr/lib -lc
+
+# flags
+CFLAGS = -Wall ${INCS} -DVERSION=\"$(VERSION)\"
+LDFLAGS = ${LIBS}
+
+# compiler
+CC = cc
+.TH IRCSRV 1 ircsrv-VERSION
+.SH NAME
+ircsrv \- a passive IRC client
+
+.SH DESCRIPTION
+.B ircsrv
+is a passive, minmalist IRC client that connects to an irc server and creates an interface to that server while maintaining the connection. ircsrv only replies to PINGs and reopens the connection when it is dropped. The input and output to and from the server are provided in their raw form.
+
+.SH SYNOPSIS
+.SY ircsrv
+.RB [ \-s
+.IR server ]
+.RB [ \-p
+.IR port ]
+.RB [ \-n
+.IR nickname ]
+.RB [ \-f
+.IR realname ]
+
+.SH OPTIONS
+.TP
+.BI \-s " server"
+lets you override the default servername (irc.freenode.net)
+.TP
+.BI \-p " port"
+lets you override the default port (6667)
+.TP
+.BI \-n " nickname"
+lets you override the default nickname ($USER) if your chosen nickname is not available, underscores will be appended until it is accepted
+.TP
+.BI \-f " realname"
+lets you specify your real name to be associated with your nick
+
+.SH AUTHOR
+Copyright \(co 2010 by Robert Lowry <robertwlowry@gmail.com>
+
+./".SH SEE ALSO
+./".BR cat (1)
+#include <err.h>
+#include <errno.h>
+#include <netdb.h>
+#include <pwd.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/socket.h>
+#include <unistd.h>
+
+#define MAX(a,b) ((a > b) ? (a) : (b))
+#define NICK_MAX 32
+
+unsigned short port = 6667;
+char *server = "irc.freenode.net";
+char nick[NICK_MAX];
+char *fullname;
+char *username;
+char *inpath;
+char *outpath;
+
+char bufin[4096];
+char bufout[4096];
+
+FILE *srv;
+FILE *in;
+FILE *out;
+
+void usage() {
+	printf("ircsrv-"VERSION" (C) MMX Robert Lowry\n");
+	printf("usage: ircsrv [-s <host>] [-p <port>] [-n <nick>] [-f <fullname>]\n");
+	exit(EXIT_SUCCESS);
+}
+
+int tcpdial(const char *host, unsigned short port) {
+	int fd;
+	struct sockaddr_in sin;
+	struct hostent *hp = gethostbyname(host);
+
+	memset(&sin, 0, sizeof(struct sockaddr_in));
+	if(!hp) err(1,"error retrieving host information");
+	sin.sin_family = AF_INET;
+	memcpy(&sin.sin_addr, hp->h_addr, hp->h_length);
+	sin.sin_port = htons(port);
+	if((fd = socket(AF_INET, SOCK_STREAM, 0)) < 0)
+		err(1,"error creating socket");
+	if(connect(fd, (const struct sockaddr *) &sin, sizeof(sin)) < 0)
+		err(1,"error connecting to host");
+	
+	return fd;
+}
+
+void reconnect() {
+	int fd = tcpdial(server,port);
+	if(srv) fclose(srv);
+	srv = fdopen(fd,"r+");
+	fprintf(srv,"NICK %s\r\n",nick);
+	fprintf(srv,"USER %s localhost %s :%s\r\n",nick,server,fullname?fullname:nick);
+	setbuf(srv,NULL);
+	fflush(srv);
+}
+
+void reregister() {
+	if(strlen(nick) > NICK_MAX) {
+		err(1,"nick name already in use");
+	} else {
+		nick[strlen(nick)] = '_';
+		nick[strlen(nick)+1] = '\0';
+		fprintf(srv,"NICK %s\r\n",nick);
+		fprintf(out,"NICK %s\r\n",nick);
+	}
+}
+
+int main (int argc, char *argv[]) {
+	struct passwd *pwd = getpwuid(getuid());
+	struct timeval tv;
+	char *t[3];
+	fd_set rd;
+	int i;
+
+	if(!pwd) err(1,"getpwuid() failed");
+	snprintf(nick, sizeof(nick), "%s", pwd->pw_name);
+	if(argc < 2 || (argc == 2 && argv[1][0] == '-' && argv[1][1] == 'h')) usage();
+	for(i=1; i + 1 < argc && (argv[i][0] == '-'); i++) {
+		switch(argv[i][1]) {
+			case 'f': fullname = argv[++i]; break;
+			case 'n': snprintf(nick,sizeof(nick),"%s",argv[++i]); break;
+			case 'p': port = strtol(argv[++i],NULL,10); break;
+			case 's': server = argv[++i]; break;
+			default: usage(); break;
+		}
+	}
+	in = stdin;
+	out = stdout;
+	setbuf(out,NULL);
+	reconnect();
+	for(;;) {
+		FD_ZERO(&rd);
+		FD_SET(fileno(in), &rd);
+		FD_SET(fileno(srv), &rd);
+		tv.tv_sec = 120;
+		tv.tv_usec = 0;
+		if((i = select(MAX(fileno(in),fileno(srv))+1, &rd, 0, 0, &tv)) < 0 && errno != EINTR)
+			err(1,"error on select()");
+		if(FD_ISSET(fileno(srv),&rd)) {
+			if(fgets(bufin, sizeof(bufin), srv) == NULL)
+				err(1,"remote host closed connection");
+			fputs(bufin,out);
+			t[0] = strtok(bufin," ");
+			for(i=1; i<3; i++)
+				t[i] = strtok(NULL," ");
+			if(t[2] && *t[0] == ':' && !strcmp(t[1],"PING")) {
+				fprintf(srv,"PONG %s\r\n",t[2]);
+				fprintf(out,"PONG %s\r\n",t[2]);
+			} else if (!t[2] && !strcmp(t[0],"PING")) {
+				fprintf(srv,"PONG %s\r\n",t[1]);
+				fprintf(out,"PONG %s\r\n",t[1]);
+			} else if (t[2] && atoi(t[1]) == 433) {
+				reregister();
+			}
+		}
+		if(FD_ISSET(fileno(in),&rd)) {
+			if(fgets(bufin, sizeof(bufin), in) == NULL)
+				err(1,"broken pipe");
+			fprintf(srv,"%s\r\n",bufin);
+		}
+	}
+	return 0;
+}
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.