+/*
+ * This module imports an "unpacked" system. The unpacked data may come from
+ * an older version of Citadel, or a different hardware architecture, or
+ * whatever. You should only run an import when your installed system is
+ * brand new and _empty_ !!
+ *
+ * $Id$
+ */
+
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include "control.h"
extern struct CitContext *ContextList;
-FILE *imfp;
+FILE *imfp, *exfp;
#define MODULE_NAME "Import an unpacked system"
#define MODULE_AUTHOR "Art Cancro"
#define MODULE_EMAIL "ajc@uncnsrd.mt-kisco.ny.us"
#define MAJOR_VERSION 0
-#define MINOR_VERSION 1
+#define MINOR_VERSION 3
static struct DLModule_Info info = {
- MODULE_NAME,
- MODULE_AUTHOR,
- MODULE_EMAIL,
- MAJOR_VERSION,
- MINOR_VERSION
-};
-
+ MODULE_NAME,
+ MODULE_AUTHOR,
+ MODULE_EMAIL,
+ MAJOR_VERSION,
+ MINOR_VERSION
+ };
-void fpgetfield(fp,string)
-FILE *fp;
-char string[];
+void fpgetfield(FILE *fp, char *string)
{
int a,b;
strcpy(string,"");
free(msgtext);
}
-void imp_floors() {
+void imp_floors(void) {
char key[256], tag[256], tval[256];
struct floor fl;
int floornum = 0;
-void imp_rooms() {
+void imp_rooms(void) {
char key[256];
char tag[256], tval[256];
int roomnum = 0;
if (!strcasecmp(tag, "qrname")) {
strcpy(qr.QRname, tval);
- lprintf(9, "<%s>", qr.QRname);
+ lprintf(9, "<%s> ", qr.QRname);
}
if (!strcasecmp(tag, "qrpasswd"))
strcpy(qr.QRpasswd, tval);
if (!strcasecmp(tag, "qrfloor"))
qr.QRfloor = atoi(tval);
if (!strcasecmp(tag, "message")) {
- lprintf(9, ".");
fpgetfield(imfp, tval);
msgnum = atol(tval);
fpgetfield(imfp, tval);
}
- lprintf(9, "\n");
+ lprintf(9, "(%d messages)\n", num_msgs);
if ((roomnum!=1)&&(qr.QRflags&QR_INUSE)) {
putroom(&qr, qr.QRname);
}
-
-
-void import_a_user() {
- char key[256], value[256], list[256];
+void import_a_user(void) {
+ char key[256], value[256];
char vkey[256], vvalue[256];
struct usersupp us;
struct quickroom qr;
struct visit vbuf;
- long *mbox = NULL;
- int mbox_size = 0;
- long msgnum;
- long msglen;
+ int visits = 0;
bzero(&us, sizeof(struct usersupp));
while(fpgetfield(imfp, key), strcasecmp(key, "enduser")) {
if ((strcasecmp(key, "mail"))
- &&(strcasecmp(key, "lastseen"))
- &&(strcasecmp(key, "generation"))
- &&(strcasecmp(key, "forget")) ) {
+ &&(strcasecmp(key, "visit")) ) {
fpgetfield(imfp, value);
}
else {
us.posted = atoi(value);
if (!strcasecmp(key, "fullname")) {
strcpy(us.fullname, value);
- lprintf(9, "User <%s>", us.fullname);
+ lprintf(9, "User <%s> ", us.fullname);
}
if (!strcasecmp(key, "axlevel"))
us.axlevel = atoi(value);
us.USscreenwidth = atoi(value);
if (!strcasecmp(key, "usscreenheight"))
us.USscreenheight = atoi(value);
- if (!strcasecmp(key, "usernum"))
+ if (!strcasecmp(key, "usernum")) {
us.usernum = atol(value);
+ lprintf(9, "<#%ld> ", us.usernum);
+ }
if (!strcasecmp(key, "lastcall"))
us.lastcall = atol(value);
if (!strcasecmp(key, "usname"))
strcpy(us.USphone, value);
if (!strcasecmp(key, "usemail"))
strcpy(us.USemail, value);
- if (!strcasecmp(key, "mail")) {
- lprintf(9, ".");
- fpgetfield(imfp, list);
- msgnum = atol(list);
- fpgetfield(imfp, list);
- msglen = atol(list);
- import_message(msgnum, msglen);
- ++mbox_size;
- mbox = realloc(mbox, (sizeof(long)*mbox_size) );
- mbox[mbox_size - 1] = msgnum;
- }
if (!strcasecmp(key, "visit")) {
+ ++visits;
bzero(&vbuf, sizeof(struct visit));
bzero(&qr, sizeof(struct quickroom));
while(fpgetfield(imfp, vkey),
strcasecmp(vkey, "endvisit")) {
- fpgetfield(imfp, value);
+ fpgetfield(imfp, vvalue);
if (!strcasecmp(vkey, "vname"))
strcpy(qr.QRname, vvalue);
if (!strcasecmp(vkey, "vgen")) {
putuser(&us, us.fullname);
- /* create a mailbox room */
- bzero(&qr, sizeof(struct quickroom));
- MailboxName(qr.QRname, &us, MAILROOM);
- qr.QRflags = QR_INUSE | QR_MAILBOX;
- time(&qr.QRgen);
- if (mbox_size > 0) qr.QRhighest = mbox[mbox_size - 1];
- putroom(&qr, qr.QRname);
-
- CC->msglist = mbox;
- CC->num_msgs = mbox_size;
- put_msglist(&qr);
-
- free(mbox);
- lprintf(9, "\n");
+ lprintf(9, "(%d rooms)\n", visits);
}
-void imp_usersupp() {
+void imp_usersupp(void) {
char key[256], value[256];
while(fpgetfield(imfp, key), strcasecmp(key, "endsection")) {
else {
strcpy(value, "");
}
- lprintf(9, " %s = %s\n", key, value);
if (!strcasecmp(key, "user")) {
import_a_user();
}
-
-
-
-void imp_globals() {
+void imp_globals(void) {
char key[256], value[256];
get_control();
-void imp_config() {
+void imp_config(void) {
char key[256], value[256];
FILE *fp;
config.c_twitdetect = atoi(value);
if (!strcasecmp(key, "c_twitroom"))
strcpy(config.c_twitroom, value);
- if (!strcasecmp(key, "c_defent"))
- config.c_defent = atoi(value);
if (!strcasecmp(key, "c_moreprompt"))
strcpy(config.c_moreprompt, value);
if (!strcasecmp(key, "c_restrict"))
-void imp_ssv() {
+void imp_ssv(void) {
char key[256], value[256];
int ssv_maxfloors = MAXFLOORS;
-void import_databases() {
+void import_databases(void) {
char section[256];
lprintf(9, " ** IMPORTING ** \n");
void do_import(char *argbuf) {
char import_filename[PATH_MAX];
-
- if (num_parms(argbuf) != 1) {
- cprintf("%d usage: IMPO unpacked_filename\n", ERROR);
- return;
- }
extract(import_filename, argbuf, 0);
imfp = fopen(import_filename, "rb");
if (imfp == NULL) {
}
import_databases();
- cprintf("%d ok\n", OK);
+ lprintf(9, "Defragmenting databases (this may take a while)...\n");
+ defrag_databases();
+ lprintf(1, "Import is finished. Shutting down Citadel...\n");
+ cprintf("%d Import finished. Shutting down Citadel...\n", OK);
+ master_cleanup();
+ }
+
+
+void dump_message(long msg_num) {
+ struct cdbdata *dmsgtext;
+
+ dmsgtext = cdb_fetch(CDB_MSGMAIN, &msg_num, sizeof(long));
+
+ if (dmsgtext == NULL) {
+ lprintf(9, "%d Can't find message %ld\n", msg_num);
+ return;
+ }
+
+ fprintf(exfp, "message%c%ld%c", 0, msg_num, 0);
+ fprintf(exfp, "%ld%c", (long)dmsgtext->len, 0);
+ fwrite(dmsgtext->ptr, dmsgtext->len, 1, exfp);
+
+ cdb_free(dmsgtext);
}
+void export_a_room(struct quickroom *qr) {
+ int b = 0;
+ int msgcount = 0;
+
+ lprintf(9,"<%s>\n", qr->QRname);
+ fprintf(exfp, "room%c", 0);
+ fprintf(exfp, "qrname%c%s%c", 0, qr->QRname, 0);
+ fprintf(exfp, "qrpasswd%c%s%c", 0, qr->QRpasswd, 0);
+ fprintf(exfp, "qrroomaide%c%ld%c", 0, qr->QRroomaide, 0);
+ fprintf(exfp, "qrhighest%c%ld%c", 0, qr->QRhighest, 0);
+ fprintf(exfp, "qrgen%c%ld%c", 0, qr->QRgen, 0);
+ fprintf(exfp, "qrflags%c%d%c", 0, qr->QRflags, 0);
+ fprintf(exfp, "qrdirname%c%s%c", 0, qr->QRdirname, 0);
+ fprintf(exfp, "qrinfo%c%ld%c", 0, qr->QRinfo, 0);
+ fprintf(exfp, "qrfloor%c%d%c", 0, qr->QRfloor, 0);
+
+ get_msglist(qr);
+ if (CC->num_msgs > 0) for (b=0; b<(CC->num_msgs); ++b) {
+ ++msgcount;
+ lprintf(9, "Message #%ld\n", MessageFromList(b));
+ dump_message(MessageFromList(b));
+ }
+
+ fprintf(exfp, "endroom%c", 0);
+ }
+
+
+void export_rooms(void) {
+ lprintf(9,"Rooms\n");
+ fprintf(exfp, "rooms%c", 0);
+ ForEachRoom(export_a_room);
+ fprintf(exfp, "endsection%c", 0);
+ }
+
+
+
+void export_floors(void) {
+ int floornum;
+ struct floor fl;
+
+ fprintf(exfp, "floors%c", 0);
+ for (floornum=0; floornum<MAXFLOORS; ++floornum) {
+ getfloor(&fl, floornum);
+ fprintf(exfp, "floor%c", 0);
+ fprintf(exfp, "f_flags%c%d%c", 0, fl.f_flags, 0);
+ fprintf(exfp, "f_name%c%s%c", 0, fl.f_name, 0);
+ fprintf(exfp, "f_ref_count%c%d%c", 0, fl.f_ref_count, 0);
+ fprintf(exfp, "endfloor%c", 0);
+ }
+ fprintf(exfp, "endsection%c", 0);
+ }
+
+
+
+
+void export_a_user(struct usersupp *us) {
+ struct cdbdata *cdbvisit;
+ struct visit *visits;
+ int num_visits;
+ int a;
+
+ lprintf(9, "User <%s>\n", us->fullname);
+
+ fprintf(exfp, "user%c", 0);
+ fprintf(exfp, "usuid%c%d%c", 0, us->USuid, 0);
+ fprintf(exfp, "password%c%s%c", 0, us->password, 0);
+ fprintf(exfp, "flags%c%d%c", 0, us->flags, 0);
+ fprintf(exfp, "timescalled%c%d%c", 0, us->timescalled, 0);
+ fprintf(exfp, "posted%c%d%c", 0, us->posted, 0);
+ fprintf(exfp, "fullname%c%s%c", 0, us->fullname, 0);
+ fprintf(exfp, "axlevel%c%d%c", 0, us->axlevel, 0);
+ fprintf(exfp, "usscreenwidth%c%d%c", 0, us->USscreenwidth, 0);
+ fprintf(exfp, "usscreenheight%c%d%c", 0, us->USscreenheight, 0);
+ fprintf(exfp, "usernum%c%ld%c", 0, us->usernum, 0);
+ fprintf(exfp, "lastcall%c%ld%c", 0, us->lastcall, 0);
+ fprintf(exfp, "usname%c%s%c", 0, us->USname, 0);
+ fprintf(exfp, "usaddr%c%s%c", 0, us->USaddr, 0);
+ fprintf(exfp, "uscity%c%s%c", 0, us->UScity, 0);
+ fprintf(exfp, "usstate%c%s%c", 0, us->USstate, 0);
+ fprintf(exfp, "uszip%c%s%c", 0, us->USzip, 0);
+ fprintf(exfp, "usphone%c%s%c", 0, us->USphone, 0);
+ fprintf(exfp, "usemail%c%s%c", 0, us->USemail, 0);
+
+
+ cdbvisit = cdb_fetch(CDB_VISIT, &CC->usersupp.usernum, sizeof(long));
+ if (cdbvisit != NULL) {
+ if ((num_visits = cdbvisit->len / sizeof(struct visit)) == 0) {
+ cdb_free(cdbvisit);
+ return;
+ }
+ visits = (struct visit *)
+ malloc(num_visits * sizeof(struct visit));
+ memcpy(visits, cdbvisit->ptr,
+ (num_visits * sizeof(struct visit)));
+ cdb_free(cdbvisit);
+
+ if (num_visits > 0) for (a=0; a<num_visits; ++a) {
+ fprintf(exfp, "visit%c", 0);
+ fprintf(exfp, "vname%c%s%c", 0,
+ visits[a].v_roomname, 0);
+ fprintf(exfp, "vgen%c%ld%c", 0,
+ visits[a].v_generation, 0);
+ fprintf(exfp, "lastseen%c%ld%c", 0,
+ visits[a].v_lastseen, 0);
+ fprintf(exfp, "flags%c%d%c", 0,
+ visits[a].v_flags, 0);
+ fprintf(exfp, "endvisit%c", 0);
+ }
+ free(visits);
+ }
+
+
+ fprintf(exfp, "enduser%c", 0);
+ }
+
+
+void export_usersupp(void) {
+ lprintf(9, "Users\n");
+ fprintf(exfp, "usersupp%c", 0);
+
+ ForEachUser(export_a_user);
+
+ fprintf(exfp, "endsection%c", 0);
+ }
+
+
+void do_export(char *argbuf) {
+ char export_filename[PATH_MAX];
+
+ extract(export_filename, argbuf, 0);
+ exfp = fopen(export_filename, "wb");
+ if (exfp == NULL) {
+ lprintf(9, "Cannot open %s: %s\n",
+ export_filename, strerror(errno));
+ cprintf("%d Cannot open file\n", ERROR);
+ return;
+ }
+
+ /* structure size variables */
+ lprintf(9, "Structure size variables\n");
+ fprintf(exfp, "ssv%c", 0);
+ fprintf(exfp, "maxfloors%c%d%c", 0, MAXFLOORS, 0);
+ fprintf(exfp, "endsection%c", 0);
+
+ /* Write out the server config */
+ lprintf(9,"Server config\n");
+ fprintf(exfp, "config%c", 0);
+ fprintf(exfp, "c_nodename%c%s%c", 0, config.c_nodename, 0);
+ fprintf(exfp, "c_fqdn%c%s%c", 0, config.c_fqdn, 0);
+ fprintf(exfp, "c_humannode%c%s%c", 0, config.c_humannode, 0);
+ fprintf(exfp, "c_phonenum%c%s%c", 0, config.c_phonenum, 0);
+ fprintf(exfp, "c_bbsuid%c%d%c", 0, config.c_bbsuid, 0);
+ fprintf(exfp, "c_creataide%c%d%c", 0, config.c_creataide, 0);
+ fprintf(exfp, "c_sleeping%c%d%c", 0, config.c_sleeping, 0);
+ fprintf(exfp, "c_initax%c%d%c", 0, config.c_initax, 0);
+ fprintf(exfp, "c_regiscall%c%d%c", 0, config.c_regiscall, 0);
+ fprintf(exfp, "c_twitdetect%c%d%c", 0, config.c_twitdetect, 0);
+ fprintf(exfp, "c_twitroom%c%s%c", 0, config.c_twitroom, 0);
+ fprintf(exfp, "c_moreprompt%c%s%c", 0, config.c_moreprompt, 0);
+ fprintf(exfp, "c_restrict%c%d%c", 0, config.c_restrict, 0);
+ fprintf(exfp, "c_bbs_city%c%s%c", 0, config.c_bbs_city, 0);
+ fprintf(exfp, "c_sysadm%c%s%c", 0, config.c_sysadm, 0);
+ fprintf(exfp, "c_bucket_dir%c%s%c", 0, config.c_bucket_dir, 0);
+ fprintf(exfp, "c_setup_level%c%d%c", 0, config.c_setup_level, 0);
+ fprintf(exfp, "c_maxsessions%c%d%c", 0, config.c_maxsessions, 0);
+ fprintf(exfp, "c_net_password%c%s%c", 0, config.c_net_password, 0);
+ fprintf(exfp, "c_port_number%c%d%c", 0, config.c_port_number, 0);
+ fprintf(exfp, "endsection%c", 0);
+
+ /* Now some global stuff */
+ lprintf(9, "Globals\n");
+ get_control();
+ fprintf(exfp, "globals%c", 0);
+ fprintf(exfp, "mmhighest%c%ld%c", 0, CitControl.MMhighest, 0);
+ fprintf(exfp, "mmnextuser%c%ld%c", 0, CitControl.MMnextuser, 0);
+ fprintf(exfp, "mmflags%c%d%c", 0, CitControl.MMflags, 0);
+ fprintf(exfp, "endsection%c", 0);
+
+ /* Export all of the databases */
+ export_rooms();
+ export_floors();
+ export_usersupp();
+
+ fprintf(exfp, "endfile%c", 0);
+ fclose(exfp);
+ lprintf(1, "Export is finished.\n");
+ cprintf("%d Export is finished.\n", OK);
+ }
+
+
+
struct DLModule_Info *Dynamic_Module_Init(void) {
CtdlRegisterProtoHook(do_import,
"IMPO",
"Import an unpacked system");
+ CtdlRegisterProtoHook(do_export,
+ "EXPO",
+ "Export the system");
return &info;
}