
#include "microdot.h"

#include "ogre.h"
#include "asyncio.h"
#include "ogre_protos.h"

//static __far UBYTE buffer[ 8192 ];

static unsigned char *buffer;
ALLOCSTATIC( buffer, 8192, MEMF_CLEAR )

extern char unregistered[];

void delspool( void )
{
	struct mbrett *sp=findbrett("/»SPOOL",0);
	struct mindex *mix;
	struct mmail *mm, *next;

	mix = loadbrettixquiet( sp );
	if( !mix )
	{
		displaybeep();
		return;
	}

	mm = ( struct mmail * ) mix->maillist.lh_Head;

	while( next = ( struct mmail * ) mm->n.mln_Succ )
	{
		if( ! ( mm->m.flags & MMF_ARCHIVE ) ) 
		{
			Remove( mm );
			mix->changed = TRUE;
		}
		mm = next;
	}
	savebrettix( mix, sp );
	freebrettix( mix );

/*	brettpfad(path,sp);
	sp->b.mails = sp->b.newmails = sp->b.unreadmails = 0;
	closeixfile( sp );
	delpathcontents(path,0,0);*/

	prefs.flags2 &= ~MDF2_REPORT;

	saveprefs( currentprefsname );
	savebretter();
	flushbrettix();
}

extern USHORT wrotenewmails;
void sendshortmail(char *emp,char *betreff,char *msg,char *bez,char *specialheader,char *specialdata, ULONG flags)
{
	char tmp[256];
	struct mbrett *spoolbrett=findbrett("/»SPOOL",0);
	struct mbrett *pm;
	struct hlist *hlist;
	struct pindex *pix;
	struct mail mail;

	hlist = hl_initheader();

	//scpy_iso2ibm( betreff, tmp );
	hl_addheader( hlist, "BET", betreff );
	//scpy_iso2ibm( emp, tmp );
	hl_addheader( hlist, "EMP", emp );
	hl_addheader( hlist, "MID", makemid());

	pm = findpmbrett( hlist );

	/* PGP-PUBLIC-KEY adden */
	if( pgpavail )
	{
		if( ( flags & 2 ) )
			pgp_addpubkey( hlist );
		else
			hl_addheader( hlist, "PGP-KEY-AVAIL", prefs.pgp_avail );
	}

	makedateheader( tmp, time(0) );
	if( prefs.ebmode & EBMODE_00 )
		memset( &tmp[8], '0', 6 );

	hl_addheader( hlist, "EDA", tmp );
	if(bez)	hl_addheader( hlist, "BEZ", bez );
	if(specialheader)
		hl_addheader( hlist, specialheader, specialdata );

	memset( &mail, 0, sizeof( mail ) );
	header2mail( hlist, &mail );
	mail.flags &= ~MMF_ARCHIVE;
	mail.flags |= MMF_UNSEEN;
	pix = msg_store( NULL, 0, msg, strlen( msg ),
		&mail.pufferID, &mail.mailID, hlist );

	mail.maillen = pix->datasize;

	storemail2ix( &mail, spoolbrett, ( flags & 1 ) ? pm : NULL, NULL );

	if( ! ( prefs.flags2 & MDF2_OWNMAILSNEW ) )
	{
		if( flags & 1 )
			pm->b.newmails--;
		/*spoolbrett->b.newmails--;*/
	}

	hl_freeheader( hlist );
	closeallixfiles();
	flushbrettix();

	wrotenewmails = TRUE;
}

void domailinglist( void )
{
	int rc;
	char mdlistname[ 80 ];
	struct mbrett *listbrett;

	rc = askreq( "Hiermit können Sie sich zur MicroDot-Mailingliste anmelden.\nEs wird automatisch ein PM-Postfach dafür eingerichtet.", "Liste bestellen|Liste abbestellen|Abbruch" );
	if( !rc )
		return;

	sendshortmail( "MicroDot-REQUEST@vapor.com", "MicroDot-Mailingliste", rc == 2 ? "UNSUBSCRIBE" : "SUBSCRIBE", 0, 0, 0, 1 );
	sprintf( mdlistname, "%s/MicroDot-Mailingliste", prefs.username );
	if( rc == 2 )
		return;

	listbrett = findbrett( mdlistname, FALSE );

	if( !listbrett )
	{
		struct brettinfo bi;

		memset( &bi, 0, sizeof( bi ) );

		// brett erzeugen
		listbrett = findbrett( mdlistname, TRUE );
		strcpy( listbrett->b.betreff, "MicroDot-Support-Mailingliste" );
		listbrett->b.flags |= BFLAG_EXTEND_PM;		

		strcpy( bi.expm_header, "ANTWORT-AN" );
		strcpy( bi.expm_data, "MicroDot@vapor.com" );
		strcpy( bi.antwortan, "MicroDot@vapor.com" );

		setbrettinfo( listbrett, &bi );
		sortbrettlist();
	}
}

void dobugreport(void)
{
	char tmp[128];
	FILE *f;
	BPTR outfile;
	void *buffer;
	long bufferlen;
	int c;
	struct Library *verlib;

	sprintf(tmp,"ram:mdbugreport.%lx",FindTask(0));

	f=fopen(tmp,"w");
	if(!f) { displaybeep(); return; }

	verlib=OldOpenLibrary("version.library");
#ifdef MDV20
	fprintf(f,"$INFO$%lx$%ld.%ld$%ld.%ld$%04lx$%s-020$%ld.%ld$%ld$\n\n",
#else
	fprintf(f,"$INFO$%lx$%ld.%ld$%ld.%ld$%04lx$%s$%ld.%ld$%ld$\n\n",
#endif
		SysBase->AttnFlags,
		SysBase->LibNode.lib_Version,SysBase->SoftVer,
		(verlib)?verlib->lib_Version:-1,(verlib)?verlib->lib_Revision:-1,
		registerinfo.serie,
		MDVER,
		ReqToolsBase->LibNode.lib_Version,
		ReqToolsBase->LibNode.lib_Revision,
		prefs.mode
	);
	CloseLibrary(verlib);
	fprintf( f, "## AUSFÜHRLICHE FEHLERBESCHREIBUNG ##\n\n\n\n" );
	fprintf( f, "## WIE WIRD DER FEHLER ERZEUGT? ##\n\n\n\n" );
	fprintf( f, "## VERHALTEN MIT ANDEREN VERSIONEN & KONFIGURATIONEN ##\n\n\n\n" );

	fprintf( f, "## MAILBOX-SOFTWARE (falls relevant) ##\n\n\n\n" );

	fclose( f );

	for(;;)
	{
		calleditor( tmp );
		c=askreq("Bugmeldung verschicken?","Ja|_Weitereditieren|Nein");
		if( c!=2 )
			break;
	}

	if(c)
	{
		bufferlen=getfilelen(tmp);
		if( bufferlen > 1 )
		{
			buffer = AllocMem(bufferlen+1,MEMF_CLEAR);
			outfile = Open( tmp, MODE_OLDFILE );
			Read( outfile, buffer, bufferlen );
			Close( outfile );
			sendshortmail("MicroDOT-Bugs@vapor.com","** BUGMELDUNG",buffer,0,"EB","",1);
			FreeMem( buffer, bufferlen + 1 );
		}
	}

	DeleteFile(tmp);
}

#include "registertxt.h"

void doregisterform(void)
{
	char tmp[128];
	FILE *f;
	BPTR outfile;
	void *buffer;
	long bufferlen;
	int c;

	if( prefs.registertime )
	{
		int days = ( time( 0 ) - prefs.registertime ) / 86400;

reask2:
		c = askreq( 
"Sie haben bereits vor %ld Tagen\n"
"ein Registrierformular verschickt.",
			"Erneut Formular verschicken|Hilfe|Abbruch", 
			days
		);

		if( !c )
			return;

		if( c == 2 )
		{
			showguide( "menu_brett_4_10" );
			goto reask2;
		}
	}

	//sprintf(tmp,"T:mdregister.%lx",FindTask(0));

	strcpy( tmp, "MD-Register-Form.txt" );

	if( !exists( tmp ) )
	{
		f=fopen(tmp,"w");
		if(!f)
		{
			displaybeep();
			return;
		}

		fprintf( f, mdregisterData,
			prefs.userrealname,
			prefs.telefon,
			prefs.username, prefs.boxname, prefs.boxdomain
		);

		fclose(f);
	}

	for(;;)
	{
		calleditor( tmp );
reask:
		c = askreq("Registrierformular verschicken?","Verschicken|_Drucken & Verschicken|_Weitereditieren|Hilfe|Nein");
		if( c == 4 )
		{
			showguide( "menu_brett_4_10" );
			goto reask;
		}

		if( c!=3 )
			break;
	}

	if( c )
	{
		bufferlen=getfilelen(tmp);
		buffer = AllocMem(bufferlen+1,MEMF_CLEAR);
		outfile = Open( tmp, MODE_OLDFILE );
		Read( outfile, buffer, bufferlen );
		Close( outfile );
		sendshortmail( "Reg-DE@vapor.com", "** MD1-Registrierung", buffer, 0, NULL, NULL, 3 );

		if( c == 2 )
		{
			f = fopen( "PRT:", "w" );
			if( f )
			{
				fwrite( buffer, bufferlen, 1, f );
				fclose( f );
			}
		}

		FreeMem( buffer, bufferlen + 1 );

		time( &prefs.registertime );
	}

	DeleteFile(tmp);
}


void sendmapsreq( int mode )
{
	char bf[ 1024 ], *p;

	if( mode == 4 )
	{
		int Done = FALSE;
		struct ogwin *ogw;
		struct IntuiMessage *im;
		struct Window *w;

		if( prefs.maps_msgprefix[ 0 ] )
		{
			BPTR f = Open( TMPMSGNAME, MODE_NEWFILE );
			Write( f, prefs.maps_msgprefix, strlen( prefs.maps_msgprefix ) );
			Close( f );
		}
		else
			DeleteFile( TMPMSGNAME );

		ogw = ogreInitWindow( scr, 0, 0, "Nachricht an MAPS" );
		ogreAddGroup( ogw, 0, OGFRAME_NONE, NULL );
		ogreAddString( ogw, 0, 'b', "_Betreff", 1, "", 40, 40 );
		ogreAddButton( ogw, 1 | OGB_ONENTER, 'v', "_Verschicken", 2 );
		ogreAddButton( ogw, 1, 'e', "Text _Editieren", 3 );
		ogreAddButton( ogw, 1 | OGB_ONESC, 'a', "_Abbruch", 4 );
		w = ogreOpenWindow( ogw );
		if( !w )
			return;

		while( !Done )
		{
			im = ogreWaitIM( ogw );

			if( im->Class == IDCMP_GADGETHELP)
				showguidenum( "mapsany_gads", im->Code );
			else if( im->Class == GADGETUP )
				switch( im->Code )
				{
					case 2: Done = 2; break;
					case 3:
						calleditor( TMPMSGNAME );
						ActivateWindow( w );
						break;
					case 4: Done = 1; break;
				}

			ogreIMReply( ogw, im );
		}

		if( Done == 2 )
		{
			int ml = getfilelen( TMPMSGNAME );
			char *msg;

			ml = max( ml, 2 );
			msg = AllocMem( ml + 1, MEMF_CLEAR );
			if( msg )
			{
				BPTR f = Open( TMPMSGNAME, MODE_OLDFILE );

				strcpy( msg, "\n" );
				if( f )
				{
					Read( f, msg, ml );
					Close( f );
				}
				sendshortmail( prefs.mapsname, ogreStringValue( ogw, 1 ), msg, 0, 0, 0, 1 );
				FreeMem( msg, ml + 1 );
			}

		}

		ogreExitWindow( ogw );

		DeleteFile( TMPMSGNAME );
		return;
	}

	switch(mode)
	{
		case 0: p = prefs.maps_list;
				break;
		case 1: p = prefs.maps_list_verbose;
				break;
		case 2: p = prefs.maps_help;
				break;
		case 3: p = prefs.maps_clearpm;
				break;
	}
	strcpy( bf, prefs.maps_msgprefix );
	strcat( bf, "\n\n" );
	sendshortmail( prefs.mapsname, p, bf, 0,0,0,1 );
}

void copyff(FILE *from,FILE *to,long len)
{
	char *buf;
	long buffsize,readlen;

	buf = allocbuffmem( len, &buffsize );

	while(len) {
		readlen=fread(buf,1,buffsize,from);
		if(readlen<1) break;
		fwrite(buf,readlen,1,to);
		len-=readlen;
	}

	freebuffmem();
}

static void *rctxtbf;
static long readconvtxt( struct msghandle *msg )
{
	long len=0, x;

	msg_initread( msg, MC_DATA );

	while( x = msg_read( msg, buffer, 2048 ) )
	{
		/*clnl( buffer );*/
		len += strlen( buffer ) + ( ( x == 1 ) ? 2 : 0 );
	}
	msg_endread( msg );
	return( len );
}

static long getnoconvcommentsize( struct msghandle *msg )
{
	return( msg->pix.commentsize );
}

static long getconvcommentsize( struct msghandle *msg )
{
	long len=0, x;

	if( !msg->pix.commentsize )
		return( 0 );

	msg_initread( msg, MC_COMMENT );

	while( x = msg_read( msg, buffer, 8192 ) )
	{
		len+=strlen(buffer) + ( ( x == 1 ) ? 2 : 0 );
	}
	msg_endread( msg );
	return( len );
}


static void copyconvtxt( struct msghandle *msg, FILE *to )
{
	int x;

	if( !msg->pix.datasize )
		return;

	msg_initread( msg, MC_DATA );

	while( x = msg_read( msg, buffer, 8192 ) )
	{
		/*clnl(buffer);*/
		//siso2ibm(buffer);
		if( x == 1 )
			fprintf( to, "%s\r\n", buffer );
		else
			fprintf( to, "%s", buffer );
	}

	msg_endread( msg );
}

void convpgpmsg( void )
{
	struct AsyncFile *f1, *f2;
	int ch;

	f1 = OpenAsync( "T:mdpgp.iso", MODE_READ, 2048 );
	f2 = OpenAsync( "T:mdpgp.txt", MODE_WRITE, 2048 );

	if( !f1 || !f2 )
	{
		if( f1 )
			CloseAsync( f1 );
		if( f2 )
			CloseAsync( f2 );
		displaybeep();
		return;
	}

	while( ( ch = ReadCharAsync( f1 ) ) != EOF )
	{
		if( ch == 10 )
			WriteCharAsync( f2, 13 );
		WriteCharAsync( f2, iso2ibm( ch ) );
	}

	CloseAsync( f1 );
	CloseAsync( f2 );
}

static void copypgp( FILE *to )
{
	struct AsyncFile *f1 = OpenAsync( "T:mdpgp.pgp", MODE_READ, 2048 );
	int ch;

	if( !f1 )
		return;

	while( ( ch = ReadCharAsync( f1 ) ) != EOF )
		fputc( ch, to );

	CloseAsync( f1 );
	DeleteFile( "T:mdpgp.txt" );
}


static void copyconvcomment( struct msghandle *msg, FILE *to )
{
	int x;

	if( !msg->pix.commentsize )
		return;

	msg_initread( msg, MC_COMMENT );

	while( x = msg_read( msg, buffer, 8192 ) )
	{
		/*clnl( buffer );*/
		//siso2ibm( buffer );
		if( x == 1 )
			fprintf( to, "%s\r\n", buffer );
		else
			fprintf( to, "%s", buffer );
	}

	msg_endread( msg );
}

#define SP_N 1
#define SP_F 2

extern int allow_trace;

static void copyfile2fp( char *file, FILE *fp )
{
	struct AsyncFile *f = OpenAsync( file, MODE_READ, 8192 );
	int ch;

	if( !f )
		return;

	while( ( ch = ReadCharAsync( f ) ) >= 0 )
	{
		if( ch == 13 )
			continue;
		if( ch == 10 )
			fputc( 13, fp );
		fputc( ch, fp );
	}

	CloseAsync( f );
}

static long getcrlflen( char *file )
{
	struct AsyncFile *f = OpenAsync( file, MODE_READ, 8192 );
	int len = 0, ch;

	if( !f )
		return( -1 );

	while( ( ch = ReadCharAsync( f ) ) >= 0 )
	{
		if( ch == 13 )
			continue;
		len++;
		if( ch == 10 )
			len++;
	}

	CloseAsync( f );

	return( len );
}


static int dospool_zc(void)
{
	FILE *puffer;
	char tmp[256],*p, *p2;
	int c,d,e,bin;
	long len;
	char line[ 4096 ];
	char mid[ 128 ];
	struct Window *iw;
	struct ogwin *ogw;
	struct mindex *mix;
	struct mbrett *spool = findbrett( "/»SPOOL", 0 );
	struct header *hl;
	struct hlist *hlist;
	struct msghandle *msg;
	struct mmail *mm;
	int pgpsign, pgpcrypt;
	int rc = 0;

	ogw = ogreInitWindow( scr, 0, NULL, "Spoole ausgehende Nachrichten..." );
	ogreAddGroup( ogw, 0, OGFRAME_NONE, NULL );
	ogreAddText( ogw, 0, "Nachricht:", SP_N, "", 46, 1 );
	ogreAddFuelGauge( ogw, 1, SP_F, 100 );
	iw = ogreOpenWindow( ogw );
	if( !iw )
		return( 0 );

	/*preport(0,1,"Spoole ausgehende Nachrichten...");
	preport(1,0,"");*/

	delpathcontents(prefs.transferdir,0,0);
	sprintf(tmp,"%sPUFFER",prefs.transferdir);
	puffer=fopen(tmp,"w");

	if(!puffer)
	{
		askreq("Fehler beim Spoolen:\nDatei '%s' läßt sich nicht öffnen (%ld)\n%s","Abbruch",tmp,_OSERR, errorstring( _OSERR ) );
		ogreExitWindow( ogw );
		return( -1 );
	}
	fsetbuf( puffer, 8192 );

	mix = loadbrettix( spool );
	if( !mix )
	{
		displaybeep();
		fclose( puffer );
		return( -2 );
	}

	flushbrettix();

	loaduserlist();

	ogreSetMaxVal( ogw, SP_F, mix->mailcount );

	for( c = 0, mm = ( struct mmail * ) mix->maillist.lh_Head; mm->n.mln_Succ; mm = ( struct mmail * ) mm->n.mln_Succ, c++ )
	{
		if( mm->m.flags & ( MMF_DEL | MMF_ARCHIVE ) )
			continue;

		msg = msg_open( mm->m.pufferID, mm->m.mailID );
		if( !msg )
		{
			displaybeep();
			continue;
		}

		sprintf( mid, "%lD (%lD Bytes Header, %lD Inhalt, %lD Kommentar)", c+1, msg->pix.headersize, msg->pix.datasize, msg->pix.commentsize );
		ogreSetStringValue( ogw, SP_N, mid );
		ogreSetValue( ogw, SP_F, c );

		hlist = msg_loadheader( msg );

		if( hl_findheader( hlist, "ABS" ) )
		{
			msg_close( msg );
			hl_freeheader( hlist );
			continue;
		}

		/* Z38-Puffer erzeugen */
		if( ISN38 )
		{
			struct header *hl, *hl2, *emp;

			/* Alle EMP:s durchgehen */
			emp = hl_findheader( hlist, "EMP" );
			while( emp )
			{
				strcpy( line, emp->data );
				p = strchr( line, ' ' );
				if( p )
					*p = 0;

				p = strchr( line, '@' );
				if( p++ )
				{
					strupr( p );
					p2 = strchr( p, '.' );
					if( p2 )
						*p2 = 0;

					if( !stricmp( prefs.boxname, p ) )
						p[-1] = 0;
					else
						strcat( p, ".ZER" );
				}

				/* Empfänger fertig */
				fprintf( puffer, "%s\r\n", line );

				/* Betreff */
				hl2 = hl_findheader( hlist, "EB" );
				hl = hl_findheader( hlist, "BET" );
				strncpy( line, hl->data, 40 );
				line[38] = 0;
				siso2ibm( line );
				if( hl2 )
					fprintf( puffer, "##%s\r\n", line );
				else
					fprintf( puffer, "%s\r\n", line );

				/* Absender */
				sprintf( line, "%s@%s.ZER", 
					prefs.username, prefs.boxname );
				strupr( strchr( line, '@' ) );
				fprintf( puffer, "%s\r\n", line );

				/* Datum */
				hl = hl_findheader( hlist, "EDA" );
				fprintf( puffer, "%10.10s\r\n", &hl->data[2] );

				/* Routpfad */
				fprintf( puffer, "\r\n" );

				/* MsgID */
				hl = hl_findheader( hlist, "MID" );
				fprintf( puffer, "%s\r\n", hl->data );

				/* Typ */
				hl = hl_findheader( hlist, "TYP" );
				if( hl )
					bin = TRUE;
				else
					bin = FALSE;
				fprintf( puffer, "%s\r\n", (bin) ? "B" : "T" );

				/* Zusätzliche Header */
				if( !bin )
				{
					len = readconvtxt( msg );

					sprintf( line, "Mailer: MicroDot " MDVER " %s\r\n",
						registerinfo.serie ? registerinfo.registriert_txt : unregistered );

					hl = hl_findheader( hlist, "BEZ" );
					while( hl )
					{
						asprintf( line, "References: <%s>\r\n",	hl->data );
						hl = hl_findnextheader( hl );
					}

					asprintf( line, "Realname: %s\r\n", prefs.userrealname );
					if(prefs.organisation[0])
						asprintf( line, "Organization: %s\r\n",prefs.organisation);
					if(prefs.telefon[0])
						asprintf( line, "Telefon: %s\r\n",prefs.telefon);
					if(prefs.postanschrift[0])
						asprintf( line, "Postanschrift: %s\r\n",prefs.postanschrift);

					strcat( line, "\r\n" );
					siso2ibm( line );
					len += strlen( line );

					fprintf( puffer, " %ld\r\n%s", len, line );
					copyconvtxt( msg, puffer );
				}
				else
				{
					fprintf( puffer, " %ld\r\n", msg->pix.datasize );
					msg_copyfp( msg, puffer, MC_DATA );
				}

				emp = hl_findnextheader( emp );				
			}
			msg_close( msg );
			hl_freeheader( hlist );
			continue;
		}

#if 0
		/* EMP: prüfen */
/*		if( strcmp( prefs.userrealname, "Oliver Wagner" ) && strcmp( prefs.boxname, "pluribus" ) )
		{*/
			hl = hl_findheader( hlist, "EMP" );
			d = 0;
			while( hl )
			{
				if( !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT" ) )
					d |= 1;
				else if( !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT-BETA" ) || !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT/BETA" ) )
				{
					d |= 2;
					hl_delheader( hl );
					hl = hl_findheader( hlist, "EMP" );
					continue;
				}

				hl = hl_findnextheader( hl );
			}
	
			if( d & 2 )
			{
				if( ! ( d & 1 ) )
					hl_addheader( hlist, "EMP", "/T-NETZ/SUPPORT/MICRODOT" );			
	
			}
//		}
#endif

		sprintf(line,"ABS: %s@%s%s (%s)\r\n",prefs.username,prefs.boxname,prefs.boxdomain,prefs.userrealname);
		siso2ibm(line);
		fputs(line,puffer);

		bin = hl_testheader( hlist, "TYP", NULL );
		pgpsign = hl_testheader( hlist, "SIGNED", "PGP" );
		pgpcrypt = hl_testheader( hlist, "CRYPT", "PGP" );
	
		hl = hl_findheader( hlist, NULL );
		do
		{
			strcpy( buffer, hl->head );
			p = strchr( buffer, 0 );
			*p++ = ':';
			*p++ = ' ';
			stccpy( p, hl->data, 7900 );
			siso2ibm( buffer );

			if( ( !stricmp( hl->head, "TYP" ) ) )
			{
				continue;
			}
			else if( !stricmp( hl->head, "MID" ) )
				strcpy( mid, hl->data );
			/*else if( !stricmp( hl->head, "BET" ) )
			{
				scpy_iso2ibm( hl->data, &buffer[ 4 ] );
			}*/
			else if( !stricmp( hl->head, "EMP" ) )
			{
				strcpy( &buffer[ 5 ], hl->data );
				if( !strchr( hl->data, '/' ) && !strchr( hl->data, '@' ) )
				{
					//scpy_iso2ibm( hl->data, &buffer[ 4 ] );
					asprintf( &buffer[5], "@%s%s",
						prefs.boxname,
						prefs.boxdomain
					);
				}
/*				else
					scpy_iso2ibm( hl->data, &buffer[ 4 ] );*/
				if( p = strchr( &buffer[ 5 ], ' ' ) )
					*p = 0;
			}
			else if( !allow_trace && !stricmp( hl->head, "TRACE" ) )
				continue;

			fprintf( puffer, "%s\r\n", buffer );

		} while( ( hl = hl_nextheader( hl ) ) );

/*		if( coded )
		{
			strupr( mid );
			mailcode = crc32( mid, strlen( mid ) );

			hl = hl_findheader( hlist, MDCRYPTHEADER );
			if( hl )
				hl_delheader( hl );

			fprintf( puffer, "%s:M%lc%lx\r\n",
				MDCRYPTHEADER,
				'A' + ( time( 0 ) % 25 ),
				mailcode
			);
			bin = FALSE;
		}*/

		sprintf( line, "MAILER: MicroDot " MDVER " %s\r\n",
			registerinfo.serie ? registerinfo.registriert_txt : unregistered );
		siso2ibm( line );
		fputs( line, puffer );

		if( !pgpcrypt )
			fputs( "CHARSET: ISO1\r\n", puffer );

		if( prefs.organisation[ 0 ] )
		{
			sprintf(line,"ORG: %s\r\n",prefs.organisation);
			siso2ibm(line);
			fputs(line,puffer);
		}
		if( prefs.telefon[ 0 ] )
		{
			sprintf( line, "TELEFON: %s\r\n", prefs.telefon );
			siso2ibm( line );
			fputs( line, puffer );
		}
		if( prefs.postanschrift[ 0 ] )
		{
			sprintf( line, "POST: %s\r\n", prefs.postanschrift );
			siso2ibm( line ); 
			fputs( line, puffer );
		}

		if( pgpsign || pgpcrypt )
		{
			DeleteFile( "T:mdpgp.iso" );
			DeleteFile( "T:mdpgp.txt" );
			DeleteFile( "T:mdpgp.pgp" );
			DeleteFile( "T:mdpgp.sig" );
			/* Nur signen */
			if( !pgpcrypt )
			{
				e = getconvcommentsize( msg );
				if( e )
				{
					fprintf( puffer, "KOM: %ld\r\n", e );
				}

				if( !bin )
				{
					msg_copy( msg, "T:mdpgp.iso", MC_COMMENT | MC_DATA );
					convpgpmsg();
					DeleteFile( "T:mdpgp.iso" );
				}
				else	/* Binär, erst Kommentar wandeln */
				{
					BPTR pgpf;

					if( e )
					{
						msg_copy( msg, "T:mdpgp.iso", MC_COMMENT );
						convpgpmsg();
						DeleteFile( "T:mdpgp.iso" );
					}

					pgpf = Open( "T:mdpgp.txt", MODE_READWRITE );
					if( !pgpf )
					{
						rc = 1;
						break;
					}
					Seek( pgpf, 0, OFFSET_END );
					msg_copyfh( msg, pgpf, MC_DATA );
					Close( pgpf );
				}

				/* Gut, in T:mdpgp.txt steht jetzt die komplette Nachricht */

				sprintf( line, "-sb -u \"%s\" -o T:mdpgp.sig T:mdpgp.txt",
					prefs.pgp_userid
				);

				if( rc = runpgp( line, 1, 2 ) )
				{
					askreq( "Fehler (%ld) beim PGP-Aufruf:\n%s", "Abbruch!", rc, line );
					rc = 1;
					break;
				}
				DeleteFile( "T:mdpgp.txt" );
				pgp_addb64hlfile( hlist, "PGP-SIG", "T:mdpgp.sig" );
				DeleteFile( "T:mdpgp.sig" );
				hl = hl_findheader( hlist, "PGP-SIG" );
				fprintf( puffer, "PGP-SIG: %s\r\n", hl->data );

				if( bin )
					fprintf( puffer, "TYP: BIN\r\n" );

				/* Verschicken */
				if( bin )
					d = msg_getsize( msg, MC_DATA );
				else
					d = readconvtxt( msg );
				fprintf( puffer, "ROT:\r\nLEN: %ld\r\n\r\n", d + e );
				if( e )
					copyconvcomment( msg, puffer );
				if( d )
				{
					if( bin )
						msg_copyfp( msg, puffer, MC_DATA );
					else
						copyconvtxt( msg, puffer );
				}

			}
			else	/* Crypt... */
			{
				e = getnoconvcommentsize( msg );
				if( e )
				{
					fprintf( puffer, "CRYPT-CONTENT-KOM: %ld\r\n", e );
				}
				if( !bin )
				{
					msg_copy( msg, "T:mdpgp.txt", MC_COMMENT | MC_DATA );
					/*convpgpmsg();
					DeleteFile( "T:mdpgp.iso" );*/
				}
				else	/* Binär, erst Kommentar wandeln */
				{
					BPTR pgpf;

					fprintf( puffer, "CRYPT-CONTENT-TYP: BIN\r\n" );

					if( e )
					{
						msg_copy( msg, "T:mdpgp.txt", MC_COMMENT );
						/*convpgpmsg();
						DeleteFile( "T:mdpgp.iso" );*/
					}

					pgpf = Open( "T:mdpgp.txt", MODE_READWRITE );
					if( !pgpf )
					{
						rc = 1;
						break;
					}
					Seek( pgpf, 0, OFFSET_END );
					msg_copyfh( msg, pgpf, MC_DATA );
					Close( pgpf );
				}

				/* Gut, in T:mdpgp.txt steht jetzt die komplette Nachricht */

				if( pgpsign )
				{
					sprintf( line, "-fes -u \"%s\" >T:mdpgp.pgp <T:mdpgp.txt",
						prefs.pgp_userid
					);
				}
				else
				{
					sprintf( line, "-fe -u \"%s\" >T:mdpgp.pgp <T:mdpgp.txt",
						prefs.pgp_userid
					);
				}


				hl = hl_findheader( hlist, "EMP" );
				while( hl )
				{
					struct user u;

					if( !getuser( hl->data, &u ) )
						asprintf( line, " \"%s\"", getuserpgpid( &u ) );

					hl = hl_findnextheader( hl );
				}

				if( rc = runpgp( line, pgpsign ? 1 : 0, 8 + ( bin ? 0 : 16 ) ) )
				{
					askreq( "Fehler (%ld) beim PGP-Aufruf:\n%s", "Huch!", rc, line );
					rc = 1;
					break;
				}
				DeleteFile( "T:mdpgp.txt" );

				/* Verschicken */

				d = getcrlflen( "T:mdpgp.pgp" );
				if( d < 0 )
				{
					askreq( "Fehler nach PGP-Aufruf\nT:mdpgp.pgp existiert nicht.", "Huch!" );
					rc = 1;
					break;
				}

				fprintf( puffer, "ROT:\r\nLEN: %ld\r\n\r\n", d );

				copyfile2fp( "T:mdpgp.pgp", puffer );
				DeleteFile( "T:mdpgp.pgp" );
			}

		}
		else if( bin )
		{
			e = getconvcommentsize( msg );
			if( e )
				fprintf( puffer, "KOM: %ld\r\n", e );
			fprintf(puffer,"TYP: BIN\r\nROT:\r\nLEN: %ld\r\n\r\n", msg_getsize( msg, MC_DATA ) + e );
			copyconvcomment( msg, puffer );
			msg_copyfp( msg, puffer, MC_DATA );
		}
		else
		{
			e = getconvcommentsize( msg );
			if( e )
				fprintf( puffer, "KOM: %ld\r\n", e );
			d = readconvtxt( msg );
			fprintf( puffer, "ROT:\r\nLEN: %ld\r\n\r\n", d + e );

			copyconvcomment( msg, puffer );

			copyconvtxt( msg, puffer );
		}

		msg_close( msg );
	}

	freeuserlist( FALSE );
	freebrettix( mix );

	if( ( prefs.key_violation == 78 ) && ftell( puffer ) )
	{
		sprintf(line,"ABS: %s@%s%s (%s)\r\n",prefs.username,prefs.boxname,prefs.boxdomain,prefs.userrealname);
		siso2ibm(line);
		fputs(line,puffer);
		makedateheader( line, time(0) );
		fprintf(puffer,"ROT:\r\nEDA: %s\r\nEMP: MicroDOT-Bugs@vapor.com\r\nBET: ** BUGMELDUNG\r\nMID: K%s\r\nLEN: %ld\r\n\r\n",line,makemid(),0);
		prefs.key_violation = 0;
	}

	fclose(puffer);

	ogreExitWindow( ogw );
	flushbrettix();

	DeleteFile( "T:mdpgp.iso" );
	DeleteFile( "T:mdpgp.txt" );
	DeleteFile( "T:mdpgp.pgp" );
	DeleteFile( "T:mdpgp.sig" );

	return( rc );
}

static void uux( char *datafile, char *cmd )
{
	char remotedataname[ 64 ];
	char localxname[ 64 ], remotexname[ 64 ], localcname[ 64 ];
	BPTR f;
	ULONG seqnum = (prefs.counter++) & 0xffff;

	pushdir( prefs.transferdir );

retry:
	/* X-File erzeugen */
	sprintf( localxname, "D.%.7sX%04lX", prefs.boxname, seqnum );
	sprintf( remotexname, "X.%.7sX%04lX", prefs.pointname, seqnum );
	sprintf( remotedataname, "D.%.7sB%04lX", prefs.pointname, seqnum );

	if( exists( localxname ) )
	{
		seqnum++;
		goto retry;
	}

	f = Open( localxname, MODE_NEWFILE );
	FPrintf( f,	"U %s %s\nF %s\nI %s\nC %s\n", prefs.username, prefs.pointname, remotedataname, remotedataname, cmd );
	Close( f );

	/* C-File erzeugen */
	sprintf( localcname, "C.%.7sN%04lX", prefs.boxname, seqnum );
	f = Open( localcname, MODE_NEWFILE );
	FPrintf( f,
		"S %s %s root - %s 0666\n"
		"S %s %s root - %s 0666\n",

		FilePart( datafile ), remotedataname, FilePart( datafile ),
		localxname, remotexname, localxname
	);
	Close( f );

	popdir();
}


#define SPECIAL(x) ((char*)(x))

static char *news_convtab[] = { 
	"LEN",			NULL,				SPECIAL(6),
	"BET",			"Subject",		0,
	"ABS", 			"From",			0,	
	"WAB", 			"Sender",			0,	
	"MID", 			"Message-ID",		SPECIAL(5),
	"EDA",			"Date",			SPECIAL(1),
	"EMP",			"Newsgroups",		SPECIAL(2),
	"ERSETZT",		"Supersedes",		0,
	"BEZ",			"References",		SPECIAL(3),
	"ROT",			"Path",			0,
	"ORG",			"Organization",	0,
	"ANTWORT-AN",	"Reply-To",		0,
	"DISKUSSION-IN","Followup-To",	SPECIAL(4),
	"STICHWORT",	"Keywords",		0,
	"MAILER",		"X-Newsreader",	0,
	"ZUSAMMENFASSUNG", "Summary",		0,
	"OAB",			"Resent-From",	0,
	"KOP", 			NULL,				SPECIAL(6),	
	"CHARSET",		NULL,				SPECIAL(7),
	"ZNETZ-TEXT",	NULL,				SPECIAL(6),
	"ZNETZ-ABS",	NULL,				SPECIAL(6),
	NULL
};

static char *mail_convtab[] = { 
	"LEN",			NULL,				SPECIAL(6),
	"BET",			"Subject",		0,
	"ABS", 			"From",			0,	
	"KOP", 			"CC",				0,	
	"WAB", 			"Sender",			0,	
	"EMP",			"To",				SPECIAL(11),
	"MID", 			"Message-ID",		SPECIAL(5),
	"EDA",			"Date",			SPECIAL(1),
	"BEZ",			"In-Reply-To",	SPECIAL(3),
	"ERSETZT",		"Supersedes",		0,
	//"ROT",			"Path",			0,
	"ROT",			NULL,				SPECIAL(6),
	"ORG",			"Organization",	0,
	"ANTWORT-AN",	"Reply-To",		0,
	"DISKUSSION-IN","Reply-To",		0,
	"STICHWORT",	"Keywords",		0,
	"MAILER",		"X-Mailer",		0,
	"OEM",			"Resent-To",		0,
	"OAB",			"Resent-From",	0,
	"ZUSAMMENFASSUNG", "Comments",	0,
	"CHARSET",		NULL,				SPECIAL(7),
	"EB",			"Return-Receipt-To", SPECIAL(8),
	"ZNETZ-TEXT",	NULL,				SPECIAL(6),
	"ZNETZ-ABS",	NULL,				SPECIAL(6),
	NULL
};

/* Date-Info */
struct ZCDateInfo
{
	time_t	t;		/* GMT */
	UBYTE 	zoneid;	/* immer 0 */
	UBYTE   flags;
	SHORT	offset;	/* relativ zur GMT in Minuten */
};

#define ZCDIF_DST 1	/* Daylightsavingtime (Sommerzeit) */

static int CLU_ZCDatestringToDI( char *ds, struct ZCDateInfo *di )
{
	char x[ 6 ], tmp[ 6 ];
	int c;

	if( !ds || !di )
		return( FALSE );

	memset( di, 0, sizeof( *di ) );

	tmp[ 2 ] = 0;
	for( c = 1; c < 6; c++ )
	{
		tmp[ 0 ] = ds[ c*2 + 2 ];
		tmp[ 1 ] = ds[ c*2 + 3 ];
		x[ c ] = atoi( tmp );
	}
	tmp[ 0 ] = ds[ 0 ];
	tmp[ 1 ] = ds[ 1 ];
	tmp[ 2 ] = ds[ 2 ];
	tmp[ 3 ] = ds[ 3 ];
	tmp[ 4 ] = 0;
	x[ 0 ] = atoi( tmp ) - 1970;
	di->t = utpack( &x[0] );

	switch( ds[ 14 ] )
	{
		case 's':
		case 'S':
			di->flags |= ZCDIF_DST;
			break;

		case 'w':
		case 'W':
			break;

		default:
			return( 0 );
			
	}

	di->offset = atoi( &ds[ 15 ] ) * 60;
	di->t += di->offset * 60;

	return( TRUE );
}

static STRPTR zc2rfcdate( STRPTR datestring, STRPTR zcdate )
{
	struct tm *ut;
	static char *mo[12] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun",
				"Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
	static char *wd[] = { "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" };
	struct ZCDateInfo di;

	CLU_ZCDatestringToDI( zcdate, &di );

	ut = localtime( &di.t );

	sprintf( datestring, "%s, %ld %s %04ld %02ld:%02ld:%02ld CET",
		wd[ ut->tm_wday ],
		ut->tm_mday, mo[ ut->tm_mon ], ut->tm_year + 1900,
	    ut->tm_hour, ut->tm_min, ut->tm_sec
	);

	return( datestring );
}

static UBYTE *sbit;
ALLOCSTATIC( sbit, 8192, 0 )

static UBYTE *string27bit( UBYTE *string )
{
	//static UBYTE sbit[ 8192 ];
	UBYTE *p = sbit;

	while( *string )
	{
		if( *string > 127 )
		{
			switch( *string )
			{
				case 132: *p++ = 'a'; *p++ = 'e'; string++; break;
				case 129: *p++ = 'u'; *p++ = 'e'; string++; break;
				case 148: *p++ = 'o'; *p++ = 'e'; string++; break;
				case 154: *p++ = 'U'; *p++ = 'e'; string++; break;
				case 142: *p++ = 'A'; *p++ = 'e'; string++; break;
				case 153: *p++ = 'O'; *p++ = 'e'; string++; break;
				case 225: *p++ = 's'; *p++ = 's'; string++; break;
				default: string++; break;
			}
		}
		else
			*p++ = *string++;
	}
	*p = 0;
	return( sbit );
}

static STRPTR ngname( STRPTR buffer, STRPTR boardname )
{
	char *p = buffer;

	strcpy( buffer, &boardname[ 1 ] );
	strlwr( buffer );

	return( buffer );
}

static struct hlist *converthh( struct hlist *header, int ispm )
{
	struct hlist *new = hl_initheader();
	struct header *hl;
	char **tab = ispm ? mail_convtab : news_convtab;
	struct hlist *emplist = hl_initheader(), *bezlist = hl_initheader(), *followlist = hl_initheader(), *tolist = hl_initheader();
	int size;

	for( hl = hl_findheader( header, NULL); hl; hl = hl_nextheader( hl ) )
	{
		char *h =  hl->head;
		char *d = string27bit( hl->data );
		char **ttab = tab;
		int skip = FALSE;

		while( *ttab && !skip )
		{
			if( !stricmp( *ttab, h ) )
			{
				switch( (int)ttab[ 2 ] )
				{
					case 0:
						hl_addheader( new, (ttab[ 1 ]), d );
						break;

					case 1:	// Dateconvert
						hl_addheader( new, (ttab[ 1 ]), zc2rfcdate( buffer, d ) );
						break;

					case 2: // EMPList
						hl_addheader( emplist, "X", ngname( buffer, d ) );
						break;

					case 3: // BEZList
						hl_addheader( bezlist, "X", d );
						break;
						
					case 4: // Followup-To POSTER
						if( d[ 0 ] == '/' )
						{
							hl_addheader( followlist, "X", ngname( buffer, d ) );
						}
						else
							hl_addheader( new, (ttab[ 1 ]), "poster" );
						break;

					case 5: // MSGID
						sprintf( buffer, "<%s>", d );
						hl_addheader( new, (ttab[ 1 ]), buffer );
						break;

					case 6: // Discard Header
						break;

					case 8: // EB
						sprintf( buffer, "%s@%s%s", prefs.username, prefs.pointname, prefs.boxdomain );
						hl_addheader( new, (ttab[ 1 ]), buffer );
						break;

					case 11: // ToList
						hl_addheader( tolist, "X", d );
						break;

				}
				skip = TRUE;
				break;
			}
			ttab += 3;
		}

		/* Nicht gefunden; entweder U-Header oder als X-Z- */
		if( !skip )
		{
			if( !strnicmp( h, "U-", 2 ) )
				hl_addheader( new, &h[ 2 ], d );
		}
	}

	/* Newsgroups konvertieren */
	for( size = 0, hl = hl_findheader( emplist, NULL ); hl; hl = hl_nextheader( hl ) )
		size += strlen( hl->data ) + 1;
	if( size )
	{
		char *bp, *bp2;

		do
		{
			bp = AllocVec( size + 1, 0 );
		} while( !bp );

		bp2 = bp;

		for( hl = hl_findheader( emplist, NULL ); hl; hl = hl_nextheader( hl ) )
		{
			strcpy( bp2, hl->data );
			strcpy( bp2 = strchr( bp2, 0 ), "," );
			bp2 += 1;
		}
		bp2[ -1 ] = 0;

		hl_addheader( new, "Newsgroups", bp );
		FreeVec( bp );
	}

	// Followup-To
	for( size = 0, hl = hl_findheader( followlist, NULL ); hl; hl = hl_nextheader( hl ) )
		size += strlen( hl->data ) + 1;
	if( size )
	{
		char *bp, *bp2;

		do
		{
			bp = AllocVec( size + 1, 0 );
		} while( !bp );

		bp2 = bp;

		for( hl = hl_findheader( followlist, NULL ); hl; hl = hl_nextheader( hl ) )
		{
			strcpy( bp2, hl->data );
			strcpy( bp2 = strchr( bp2, 0 ), "," );
			bp2 += 1;
		}
		bp2[ -1 ] = 0;

		hl_addheader( new, "Followup-To", bp );
		FreeVec( bp );
	}

	/* To konvertieren */
	for( size = 0, hl = hl_findheader( tolist, NULL ); hl; hl = hl_nextheader( hl ) )
		size += strlen( hl->data ) + 3;
	if( size )
	{
		char *bp, *bp2;

		do
		{
			bp = AllocVec( size + 1, 0 );
		} while( !bp );

		bp2 = bp;

		for( hl = hl_findheader( tolist, NULL ); hl; hl = hl_nextheader( hl ) )
		{
			strcpy( bp2, hl->data );
			strcpy( bp2 = strchr( bp2, 0 ), ", " );
			bp2 += 2;
		}
		bp2[ -2 ] = 0;

		hl_addheader( new, "To", bp );
		FreeVec( bp );
	}

	/* References-Zeilen konvertieren */
	for( size = 0, hl = hl_findheader( bezlist, NULL ); hl; hl = hl_nextheader( hl ) )
		size += strlen( hl->data ) + 3;
	if( size )
	{
		char *bp, *bp2;

		do
		{
			bp = AllocVec( size + 1, 0 );
		} while( !bp );

		bp2 = bp;

		for( hl = hl_findheader( bezlist, NULL ); hl; hl = hl_nextheader( hl ) )
		{
			*bp2++ = '<';
			strcpy( bp2, hl->data );
			strcpy( bp2 = strchr( bp2, 0 ), "> " );
			bp2 += 2;
		}
		bp2[ -1 ] = 0;

		hl_addheader( new, ispm ? "In-Reply-To" : "References", bp );
		FreeVec( bp );
	}

	hl_freeheader( emplist );
	hl_freeheader( bezlist );
	hl_freeheader( followlist );
	hl_freeheader( tolist );

	return( new );
}

static void uuencode( char *filename )
{
	FILE *to = fopen( "T:msg.tmp", "a" ), *f2 = fopen( "T:msg.uue", "r" );
	int blocksize;

	fprintf( to, "begin 644 %s\n", filename );
	
	for(;;)
	{
		UBYTE *memblock = buffer;

		blocksize = fread( buffer, 1, 1800, f2 );
		if( blocksize < 1 )
			break;
		while( blocksize )
		{
			int bytes = min( 45, blocksize );
			int c;

			blocksize -= bytes;

			fputc( 32 + bytes, to );

			for( c = 0; c < bytes; c += 3 )
			{
				int b1 = memblock[ c ], b2 = memblock[ c + 1 ], b3 = memblock[ c + 2 ];
				int ch1, ch2, ch3, ch4;

				ch1 = ' ' + ( b1 >> 2 );
				ch2 = ' ' + ( ( b1 & 0x3 ) << 4 ) + ( b2 >> 4 );
				ch3 = ' ' + ( ( b2 & 0xf ) << 2 ) + ( ( b3 >> 6 ) );
				ch4 = ' ' + ( b3 & 0x3f );

				fputc( ch1, to );
				fputc( ch2, to );

				if( bytes - c > 2 )
				{
					fputc( ch3, to );
					fputc( ch4, to );
				}
			}

			memblock += bytes;

			fprintf( to, "X\n" );
		}
	}
	fprintf( to, " X\nend\n" );
	fclose( f2 );
	fclose( to );
	DeleteFile( "T:msg.uue" );
}

static void make7bit( void )
{
	FILE *f1 = fopen( "T:msg.tmp", "w" ), *f2 = fopen( "T:msg.8bit", "r" );
	int rc, c;

	for(;;)
	{
		rc = fread( buffer, 1, 2048, f2 );
		if( rc < 1 )
			break;
		for( c = 0; c < rc; c++ )
		{
			switch( buffer[ c ] )
			{
				case 228: fputc( 'a', f1 ); fputc( 'e', f1 ); break;
				case 252: fputc( 'u', f1 ); fputc( 'e', f1 ); break;
				case 246: fputc( 'o', f1 ); fputc( 'e', f1 ); break;
				case 220: fputc( 'U', f1 ); fputc( 'e', f1 ); break;
				case 196: fputc( 'A', f1 ); fputc( 'e', f1 ); break;
				case 214: fputc( 'O', f1 ); fputc( 'e', f1 ); break;
				case 223: fputc( 's', f1 ); fputc( 's', f1 ); break;
				default: fputc( buffer[ c ], f1 ); break;
			}
		}
	}
	fclose( f1 );
	fclose( f2 );
	DeleteFile( "T:msg.8bit" );
}

static int dospool_rfc(void)
{
	FILE *puffer = NULL, *cp;
	int c, d, bin;
	char line[1024];
	char mid[128];
	struct Window *iw;
	struct ogwin *ogw;
	struct mindex *mix;
	struct mbrett *spool = findbrett( "/»SPOOL", 0 );
	struct header *hl;
	struct hlist *hlist, *newhlist;
	struct msghandle *msg;
	struct mmail *mm;
	int pgpsign, pgpcrypt;
	int rc = 0;
	char news_dname[ 64 ], mail_dname[ 64 ];
	int ispm, rnewspos;

	ogw = ogreInitWindow( scr, 0, NULL, "Spoole ausgehende Nachrichten..." );
	ogreAddGroup( ogw, 0, OGFRAME_NONE, NULL );
	ogreAddText( ogw, 0, "Nachricht:", SP_N, "", 46, 1 );
	ogreAddFuelGauge( ogw, 1, SP_F, 100 );
	iw = ogreOpenWindow( ogw );
	if( !iw )
		return( 0 );

	mix = loadbrettix( spool );
	if( !mix )
	{
		displaybeep();
		return( -2 );
	}

	flushbrettix();
	loaduserlist();

	ogreSetMaxVal( ogw, SP_F, mix->mailcount );

	sprintf( news_dname, "D.%-.7sD%04lx", prefs.boxname, (prefs.counter++)&0xffff );

	for( c = 0, mm = ( struct mmail * ) mix->maillist.lh_Head; mm->n.mln_Succ; mm = ( struct mmail * ) mm->n.mln_Succ, c++ )
	{
		if( mm->m.flags & ( MMF_DEL | MMF_ARCHIVE ) )
			continue;

		msg = msg_open( mm->m.pufferID, mm->m.mailID );
		if( !msg )
		{
			displaybeep();
			continue;
		}

		sprintf( mid, "%lD (%lD Bytes Header, %lD Inhalt, %lD Kommentar)", c+1, msg->pix.headersize, msg->pix.datasize, msg->pix.commentsize );
		ogreSetStringValue( ogw, SP_N, mid );
		ogreSetValue( ogw, SP_F, c );

		hlist = msg_loadheader( msg );

		if( hl_findheader( hlist, "ABS" ) )
		{
			msg_close( msg );
			hl_freeheader( hlist );
			continue;
		}

#if 0
		/* EMP: prüfen */
/*		if( strcmp( prefs.userrealname, "Oliver Wagner" ) && strcmp( prefs.boxname, "pluribus" ) )
		{*/
			hl = hl_findheader( hlist, "EMP" );
			d = 0;
			while( hl )
			{
				if( !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT" ) )
					d |= 1;
				else if( !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT-BETA" ) || !stricmp( hl->data, "/T-NETZ/SUPPORT/MICRODOT/BETA" ) )
				{
					d |= 2;
					hl_delheader( hl );
					hl = hl_findheader( hlist, "EMP" );
					continue;
				}

				hl = hl_findnextheader( hl );
			}
	
			if( d & 2 )
			{
				if( ! ( d & 1 ) )
					hl_addheader( hlist, "EMP", "/T-NETZ/SUPPORT/MICRODOT" );			
			}
//		}
#endif

		hl = hl_findheader( hlist, "EMP" );
		ispm = FALSE;
		while( hl )
		{
			if( hl->data[ 0 ] != '/' )
				ispm = TRUE;
			hl = hl_findnextheader( hl );
		}

		// Nun gut, falls PM, Puffer öffnen
		if( ispm )
		{
			pushdir( prefs.transferdir );
			sprintf( mail_dname, "D.%-.7sD%04lx", prefs.boxname, (prefs.counter++)&0xffff );
			cp = fopen( mail_dname, "w" );
			popdir();

			// From schreiben
			fprintf( cp, "From %s remote from %s\n", prefs.username, prefs.pointname );
		}
		else
		{
			if( !puffer )
			{
				pushdir( prefs.transferdir );
				puffer = fopen( news_dname, "w" );
				popdir();
			}
			cp = puffer;
			rnewspos = ftell( cp );
			fprintf( cp, "#! rnews 00000000\n" );
		}

		// From: erzeugen

		fprintf( cp, "From: %s@%s%s (%s)\n", prefs.username, prefs.pointname, prefs.boxdomain, prefs.userrealname );

		bin = hl_testheader( hlist, "TYP", NULL );
		pgpsign = hl_testheader( hlist, "SIGNED", "PGP" );
		pgpcrypt = hl_testheader( hlist, "CRYPT", "PGP" );

		newhlist = converthh( hlist, ispm );
		hl = hl_findheader( newhlist, NULL );
		do
		{
			fprintf( cp, "%s: %s\n", hl->head, hl->data );
		} while( ( hl = hl_nextheader( hl ) ) );

		fprintf( cp, "X-%s: MicroDot " MDVER " %s\n", ispm ? "Mailer" : "Newsreader",
			registerinfo.serie ? registerinfo.registriert_txt : unregistered );

		if( prefs.organisation[ 0 ] )
		{
			fprintf( cp, "Organization: %s\n",prefs.organisation);
		}

		if( !ispm )
			fprintf( cp, "Path: %s.%s!not-for-mail\n", prefs.pointname, ( prefs.boxdomain[ 0 ] == '.' ) ? &prefs.boxdomain[ 1 ] : prefs.boxdomain );

		// Nun die Nachricht auslagern

		DeleteFile( "T:msg.tmp" );

		// Falls Binär, UUEncoden
		if( bin )
		{
			hl = hl_findheader( hlist, "FILE" );
			if( !hl )
				hl = hl_findheader( hlist, "BET" );

			DeleteFile( "T:msg.uue" );
			msg_copy( msg, "T:msg.uue", MC_DATA );
			msg_copy( msg, "T:msg.tmp", MC_COMMENT );
			uuencode( hl->data );
		}
		else if( ispm || !prefs.rfc_newsfmt )
		{
			DeleteFile( "T:msg.8bit" );
			msg_copy( msg, "T:msg.8bit", MC_COMMENT | MC_DATA );
			make7bit();
		}
		else
		{
			msg_copy( msg, "T:msg.tmp", MC_COMMENT | MC_DATA );
			fprintf( cp, "Mime-Version: 1.0\nContent-Type: text/plain; charset=ISO-8859-1\nContent-Transfer-Encoding: 8bit\n" ); 
		}

		if( pgpsign || pgpcrypt )
		{
			DeleteFile( "T:msg.pgp" );
			/* Nur signen */
			if( !pgpcrypt )
			{
				/* Gut, in T:mdpgp.txt steht jetzt die komplette Nachricht */

				sprintf( line, "-s -u \"%s\" -o T:msg.pgp T:msg.tmp",
					prefs.pgp_userid
				);

				if( rc = runpgp( line, 1, 2 ) )
				{
					askreq( "Fehler (%ld) beim PGP-Aufruf:\n%s", "Huch!", rc, line );
					rc = 1;
					break;
				}

			}
			else	/* Crypt... */
			{
				if( pgpsign )
				{
					sprintf( line, "-es -u \"%s\" -o T:msg.pgp T:msg.tmp",
						prefs.pgp_userid
					);
				}
				else
				{
					sprintf( line, "-e -u \"%s\" -o T:msg.pgp T:msg.tmp",
						prefs.pgp_userid
					);
				}


				hl = hl_findheader( hlist, "EMP" );
				while( hl )
				{
					struct user u;

					if( !getuser( hl->data, &u ) )
						asprintf( line, " \"%s\"", getuserpgpid( &u ) );

					hl = hl_findnextheader( hl );
				}

				if( rc = runpgp( line, pgpsign ? 1 : 0, 8 ) )
				{
					askreq( "Fehler (%ld) beim PGP-Aufruf:\n%s", "Huch!", rc, line );
					rc = 1;
					break;
				}
			}
			DeleteFile( "T:msg.tmp" );
			Rename( "T:msg.pgp", "T:msg.tmp" );
		}

		// Nun "msg.tmp" an den Puffer anhängen
		fprintf( cp, "\n" );	// Leerzeile
		{
			FILE *f2 = fopen( "T:msg.tmp", "r" );
			while( f2 )
			{
				int rc = fread( buffer, 1, 2048, f2 );
				if( rc < 1 )
				{
					fclose( f2 );
					break;
				}
				fwrite( buffer, rc, 1, cp ); 
			}
		}
		msg_close( msg );

		if( ispm )
		{
			fclose( cp );
			strcpy( buffer, "rmail" );
			hl = hl_findheader( hlist, "EMP" ); // Alte liste
			ispm = FALSE;
			while( hl )
			{
				if( hl->data[ 0 ] != '/' )
				{
					char tmp[ 256 ], *p;

					strcat( buffer, " " );
					strcpy( tmp, hl->data );
					p = stpbrk( tmp, " \t" );
					if( p )
						*p = 0;
					p = strrchr( tmp, '@' );
					if( p )
					{
						*p++ = 0;
						strcat( buffer, p );
						strcat( buffer, "!" );
					}
					strcat( buffer, tmp );
				}
				hl = hl_findnextheader( hl );
			}
			uux( mail_dname, buffer );
		}
		else
		{
			int newpos = ftell( cp );
			fseek( cp, rnewspos + 9, 0 );
			fprintf( cp, "%08ld", newpos - rnewspos - 18 );
			fseek( cp, 0, 2 );
		}

		hl_freeheader( hlist );
		hl_freeheader( newhlist );
	}

	if( puffer )
	{
		fclose( puffer );
		uux( news_dname, "rnews" );
	}

	freeuserlist( FALSE );
	freebrettix( mix );

	ogreExitWindow( ogw );
	flushbrettix();

	DeleteFile( "T:msg.tmp" );
	DeleteFile( "T:msg.pgp" );

	delspool();

	return( rc );
}

int dospool( void )
{
	if( prefs.mode == MDM_RFC )
		return( dospool_rfc() );
	else
		return( dospool_zc() );
}
