WinFlex
A WinSock based client for FlexFax
Version 0.3 (Beta)


Copyright 1993 by Peter Bentley <pete@tecc.co.uk>

Permission to use, copy, modify, distribute, and sell this software and its documentation for 
any purpose is hereby granted without fee, provided that the above copyright notice appear in 
all copies and that both that copyright notice and this permission notice appear in supporting 
documentation, and that the name of Peter Bentley not be used in advertising or publicity 
pertaining to distribution of the software without specific, written prior permission.  Peter 
Bentley makes no representations about the suitability of this software for any purpose.  It is 
provided "as is" without express or implied warranty. 
PETER BENTLEY DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, 
INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN 
NO EVENT SHALL PETER BENTLEY BE LIABLE FOR ANY SPECIAL, INDIRECT OR 
CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS 
OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE 
OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE 
USE OR PERFORMANCE OF THIS SOFTWARE. 


What is WinFlex?
WinFlex is a simple Windows 3 client for the Unix based FlexFax network fax system.  The 
current version allows single PostScript files to be spooled to a FlexFax host for faxing to a 
single destination across a TCP/IP network.
WinFlex can be set up to automatically fax all data sent to a specific file, on the assumption 
that this file has been set up as a Windows printer 'port'.  WinFlex interacts with the Print 
Manager to try and ensure data is collected from this file at the correct time.
WinFlex can also generate cover sheets to go with the document you are faxing.  Like the Unix 
FlexFax, cover sheets are produced from a PostScript template file.  WinFlex fills in some of 
the details, and provides a dialogue box for the user to fill in the rest.
Version
This document describes version 0.3, a BETA release.  It works for me in as much as it 
submits PostScript files to my local FlexFax server. Your mileage may vary.  If WinFlex runs 
amok, nukes your hard disk, has sex with your cat, or anything like that then you are on your 
own.
Don't forget to scan the executable for viruses before you run it. I know I haven't got any, but 
you shouldn't take my word for it...
Installation
WinFlex is distributed as two ZIP files.  WFLX03X.ZIP contains the executable and this 
document in Word for Windows format (WINFLEX.DOC) and in ASCII (WINFLEX.TXT).  
WFLX03S.ZIP contains another copy of this document and the source code 
Before you start, you will need a working Winsock DLL, and a FlexFax host which your 
machine has permission to use.  You should configure your Winsock DLL so that it knows that 
port 4557 is the fax service (or whatever you use).  For a Winsock DLL that uses a BSD-style 
services file, add a line like:- 
fax		4557/tcp	flexfax	#Fax transmission service 
Note also that your Winsock DLL file must either be in a directory on your PATH, your 
Windows directory, or your Windows System directory (often C:\WINDOWS\SYSTEM).  Winflex 
will run without an entry like this, but will complain every time it connects to the server (and will 
assume a port number of 4557).
To install WinFlex itself, put the executable (WINFLEX.EXE) in a directory somewhere and 
add an entry for it in a Program Manager group (or whatever shell you use in its place). Run it 
and select File|Settings to set up the name of your fax host, your username on the fax host 
machine, your full name and Email address. These settings will be saved in your WIN.INI, so 
you only need to enter them once. 
If you wish to generate cover pages locally, then you will need to fill in the "Template File" box 
in the dialogue to point at a suitable cover sheet template.  If you do not know how FlexFax 
cover templates work, ask your local FlexFax administrator.  If you are the local administrator, 
then RTFM, as this is something you should know...
Printing directly to FlexFax
WinFlex can be set up to allow you to print PostScript from your applications that will be 
spooled directly to your FlexFax server.  To do this you need to dedicate a directory on your 
computer for spooling PostScript files to.  Then you set up an entry in the [ports] section of 
your WIN.INI which will allow you to connect a PostScript printer directly to a file in that 
directory.  Eg, your WIN.INI might look like this after you have added the line:-
[ports]
LPT1:=
LPT2:=
C:\SPOOL\KXP4420.SPL=
Finally you tell FlexFax the name of the directory and the name of the spool file, and it will 
monitor the Print Manager and when appropriate move the contents of the spool file to a safe 
place, and pop up the usual 'Send Fax' dialogue for you to specify the recipient.
In fact, WinFlex can handle most of this setup for you.  Decide the name of the directory you 
wish to use  (eg C:\SPOOL) and a spool file name (eg FLEXFAX.SPL).  Type these entries 
into the WinFlex setup dialogue.  When you click OK, WinFlex will offer to create the directory 
if it does not already exist, and will also offer to create the entry in your WIN.INI.  You can 
then go straight to the Control Panel, and use the Connect... dialogue to attach a 
PostScript printer to the new port.  It is imperative that you check the 'Use Print Manager'' box 
on the Control Panel's Printers dialogue, or nothing will work...
Usage
If you have selected auto-print in the setup dialogue box, then simply run WinFlex minimised.  
Now go into an application and print something to the PostScript printer attached to WinFlex' 
spool file.  After the application has finished printing, WinFlex will pop up a dialogue box to fill 
in the destination fax number.  If you have installed a cover sheet template, you may also fill in 
the cover sheet related fields in the dialogue, and they will be incorporated into the cover 
sheet.  WinFlex will automatically fill in the Date, Number of Pages and Sender fields.  Click 
OK, and the fax should get sent.  If everything goes will, the last thing you will see on the 
status dialogue is the job ID that FlexFax (on the fax server) has allocated for your fax.  Select 
OK, and WinFlex will remove the status dialogue and remove the PostScript file from your local 
hard disk.
If it doesn't work, and the reason is not obvious, mail me with as much information as you can 
(especially the contents of the various status fields).  Unfortunately, WinFlex may occaisionally 
leave an incorrect status message in the dialogue (just to confuse you).
If you have a PostScript file on your disk that you wish to fax manually, just select the File|Fax 
option in WinFlex, and enter the name of the file.  The rest of the process is as for an auto-
print file.
Getting the Server Status
Select Status|Send to look at the server send queue, and Status|Receive to see the received 
faxes (if they are publically viewable).  The status code is extremely flakey.  Sorry.  In fact, the 
receive queue status isn't parsed at all, so will probably make no sense to any sane human.

Limitations (numerous)

	o	Only a single PostScript file can be faxed at a time
	o	Only a single destination can be specified
	o	No way of specifying submission time etc etc
	o	No support for file formats other than PostScript
	o	No online help, poor documentation
	o	No equivalent to FAXRM to kill jobs
	o	Fax server status code is very very preliminary
	o	No way of viewing or retrieving faxes, even if the receive queue is public
	o	Error messages will be mailed to you on the Unix host
	o	No way of selecting different fax modems on Unix hosts
	o	No database of available FlexFax hosts
	o	No local database of fax numbers, names, companies etc
	o	Not terribly efficient socket code
I plan to fix all of these deficiencies, probably more or less in the order they're listed.  If I get 
requests for a particular feature, I'll move it up the list. 
Feedback
Email me (pete@tecc.co.uk) if WinFlex works on your machine.  In particular I would like 
to know things like:- 
	o	Brand of Winsock.DLL, 
	o	Hardware (ethernet card, packet driver etc) 
	o	Version of FlexFax on the Unix host. 
If I get no feedback, I will assume no-one is using this program, and adjust the time I spend 
developing it accordingly... 
If WinFlex doesn't work on your machine, then I would be even more interested in hearing from 
you so I can fix it. 
Copyright
Do what you like with this program apart from removing the copyright notices. 
This program is "beerware".  If you find it useful, then the next time you meet the author in a 
pub, you should seriously consider buying him a beer. 
Building From Source Code
You will need the zApp application framework and a Borland C++ compiler (Turbo C for 
Windows/BC++3.0/BC++3.).  I have not yet found a free class library for Windows that saves 
me from the pain of the Windows C API.  I rather like zApp (I chose it after writing the same 
little application using OWL, zApp and Zinc for comparison), but I am not associated with 
Inmark (its authors) in any way.
Anyway, building from source should be as easy as getting the source code, loading the .PRJ 
file into your C++ compiler and hitting 'make'. Check the directories in the project file first, 
though...
The enclosed winsock.h came directly from rhino.microsoft.com. The enclosed 
winsock.lib came by running IMPLIB on a Winsock DLL.
Source Code Layout
The application is split into three main parts:- 
	tcSock.h/tcSock.cpp	TECC Winsock classes
	ffClient.h/ffClient.cpp	FlexFax client classes
	WinFlex.h/WinFlex.cpp	The WinFlex application code
The TECC sockets classes are something I did as an experiment.  They use the WSA...() 
asynchronous Winsock calls.  User code is added by deriving from tcSocket and overriding 
appropriate member functions (eg the Connected() member is called when a connect() 
completes). The derived classes tcBufSocket and tcLineBufSocket provide buffering 
on top of a tcSocket and different callbacks (eg  tcLineBufSocket::lineRead() is 
called when a complete line of text is available on the socket).  The buffering in these classes 
isn't very well done, and I shall probably restructure it soon to get rid of a load of redundant 
data copying, so don't rely on this interface staying the same.  I shall also try and do something 
to make accept() work a little better for server sockets... 
Whenever at least one instance of a tcSocket is created, then a tcSocketManager is 
also created.  This tells the top level zApp window to pass any WM_SOCKET messages to it.  It 
then maintains a list of active tcSockets.  WM_SOCKET is defined in tcSocket.h, and if it 
clashes with a message number you are using, just redefine it.  Each tcSocket keeps a 
mask of events it is interested in (eg FD_READ and FD_CLOSE), and whenever this mask is 
changed using the addMask() or delMask() member function, it calls 
WSAAsynchSelect() telling Winsock to pass a WM_SOCKET message to the zApp base 
window when the event occurs.  zApp will then invoke the socket manager's 
sockHandler() member, which will find the corresponding tcSocket from its list, and will 
invoke a suitable member function.
The ffClient stuff is basically a load of structs to hold the data describing a fax job 
(ffJob), and ffSocket, a tcSocket which 'knows' the FlexFax protocol and can use it to 
submit a job to a FlexFax server.  The ffSocket works as a simple state machine.  Its 
current state determines what it will do next (eg transmit some more data).  State transitions 
are triggered either from callbacks from tcLineBufSocket, or by running out of data to 
transmit in the current state.
The WinFlex application is mostly just a top-level shell which handles the menus, some simple 
dialogues to put a ffJob together and creation of an ffSocket to submit the job to the 
server.   Possibly of interest is the code which handles auto-printing to FlexFax.  It uses zApp 
to invoke a handler when a WM_SPOOLERSTATUS message is delivered.  When this message 
indicates that the Print Manager's queue is empty, then we can be nearly certain that if there is 
any data in out spool file, then it is a complete print job, and that the Print Manager will remain 
idle until we return from the message handler.  So, we look for data in the spool file, and if we 
find some that looks valid, we rename the file and create an ffJob to send it to the FlexFax 
server.  Then we delete the file...
Porting to other Application Frameworks
Currently the tcSocket classes require zApp for message handling, but this is pretty 
localised to the tcSockManager class.  Also the ffJobDialogue class uses a zApp 
dialogue class, but this is also pretty localised.  Everything else could probably be ported to 
another Windowing framework.  If you do this, then please let me have the code so I can 
merge it into WinFlex. 
If you add any useful enhancements/bug fixes to any of this, then please pass any feedback to 
me as pete@tecc.co.uk...
