[hamradio-commits] [axmail] 01/04: Imported Upstream version 2.5

Dave Hibberd hibby-guest at moszumanska.debian.org
Sat Sep 19 21:39:31 UTC 2015


This is an automated email from the git hooks/post-receive script.

hibby-guest pushed a commit to branch master
in repository axmail.

commit 4e24dd9ccceeb4d0158640e8748de5e45903fd89
Author: Dave Hibberd <d at vehibberd.com>
Date:   Sat Sep 19 11:10:57 2015 +0100

    Imported Upstream version 2.5
---
 FAQ                  | 116 ++++++++++++
 INSTALL              |  62 ++++++
 LICENSE              | 339 +++++++++++++++++++++++++++++++++
 Makefile             |  52 +++++
 README               | 374 ++++++++++++++++++++++++++++++++++++
 UPGRADING            |   6 +
 adduser.c            | 193 +++++++++++++++++++
 adduser.h            |   2 +
 axmail.c             | 297 +++++++++++++++++++++++++++++
 axmail.h             |   4 +
 command.c            | 148 +++++++++++++++
 command.h            |   9 +
 config.c             | 285 ++++++++++++++++++++++++++++
 config.h             |  44 +++++
 copying              | 340 +++++++++++++++++++++++++++++++++
 defines.h            |  31 +++
 etc/axmail.conf      |  53 ++++++
 etc/help/autofwd.hlp |  11 ++
 etc/help/delete.hlp  |  10 +
 etc/help/help.hlp    |   7 +
 etc/help/info.hlp    |   2 +
 etc/help/kill.hlp    |  10 +
 etc/help/send.hlp    |   7 +
 etc/help/sfax.hlp    |  20 ++
 etc/welcome.txt      |  11 ++
 head.c               | 214 +++++++++++++++++++++
 head.h               |  19 ++
 lock.c               |  36 ++++
 lock.h               |   3 +
 mailcmd.c            | 526 +++++++++++++++++++++++++++++++++++++++++++++++++++
 mailcmd.h            |   9 +
 mbox.c               | 357 ++++++++++++++++++++++++++++++++++
 mbox.h               |  46 +++++
 quit.c               | 250 ++++++++++++++++++++++++
 quit.h               |   2 +
 setpwnam.c           | 212 +++++++++++++++++++++
 setpwnam.h           |   5 +
 utils.c              | 167 ++++++++++++++++
 utils.h              |  15 ++
 39 files changed, 4294 insertions(+)

diff --git a/FAQ b/FAQ
new file mode 100644
index 0000000..576984b
--- /dev/null
+++ b/FAQ
@@ -0,0 +1,116 @@
+axMail - an SMTP mailbox for the various linux node frontends.
+
+axMail appears to work with most linux based MTAs (Mail Transport Agent)
+but not all, and I haven't had a chance to test it with them all either, 
+nor do I honestly care to install every MTA available for linux to do such 
+so if you do run an MTA *not listed* below, please feel free to email me 
+at: <n1uro at n1uro.com> and I'll add your report to this list. Consider this 
+file a 'work in progress' as with the software itself. How to test is 
+listed at the bottom.
+
+PostFix   - tested fine
+Exim      - tested fine
+Smail**   - failed tests, and also causes a total loss of end user mail!
+Sendmail* - <unknown>
+Qmail***  - <unknown>
+
+*  - In theory, the sendmail MTA should be ok since both exim and postfix
+     have sendmail compatable binaries/symlinks/etc.
+
+** - I don't know what it is with the smail MTA, but for some reason *all* 
+     mail gets lost during the internal transfers from the system mailbox 
+     and back to the system mailbox. Since smail has basically been 
+     abandoned in favor of exim, I don't personally foresee this as an
+     issue.
+
+***- I've never installed a qmail system before and honestly don't feel
+     like doing that now hi!.. so if you run qmail and it works ok, please
+     let me know and I'll change it's status
+
+If there's an MTA that I have missed and you've tested it and it works 
+please inform me and I'll add your results here.
+
+
+How to test axmail:
+
+You can run axmail at a command prompt!.. all it requires is that you put 
+your callsign after it. BEFORE you run this via a commandline however I 
+strongly suggest you make a backup of your system mail spool file by 
+typing: cp /var/spool/mail/call /var/spool/mail/call.bak this way here if 
+there is an issue and you have mail waiting, you won't lose any mail.
+
+I'll assume your account on your box is your callsign, so in my case I would 
+execute: 
+n1uro at nat-client0:~$ /usr/sbin/axmail n1uro
+and the standard greetings should appear along with the prompt and any
+mail waiting should appear listed.
+
+Pending the above test worked ok and unread/undeleted mail was saved back 
+into the system mailbox, try it from the node as a user who doesn't have 
+an account on the box. Hopefully when you exit, it'll tell you that you 
+have new mail waiting! Go back in and you should see the welcome.txt file 
+from /etc/ax25 listed as a greeting email message.
+
+Other quick FAQs:
+
+axMail works by comparing the user's system mail spool file, and as well 
+as any existing axMail saved mail and merges them together 'offline' for 
+lack of a better word to use. It then takes this mail and allows the user 
+to read/reply/delete/save/etc. 
+
+axMail has *always* supported file attachments, after all a file attachment
+is just an encoded file appended to the body of the email message... its just
+that most every client now-a-day automatically encodes/decodes them for you
+and you assume that a file attachment is a seperate entity. All you need to
+do to send and receive attachments via a packet terminal is the following
+(examples taken from a linux terminal);
+
+Sending: First encode the file by using uuencode. To do this run 
+uuencode filename filename
+or if you want to make a file of it run: uuencode file file > file1
+then copy and paste that encoded text in it's full into the body of
+the mail message and send it.
+
+Receiving: copy and paste the output of your message into a temporary
+file and then run "uudecode -o filename tempfile". You will now have
+a pdf/doc/text/jpg file sent to you by someone.
+
+axMail now supports sending of fax transmissions! To configure axMail to
+be able to do such, configure an account with an online fax service such
+as eFax where you can email faxes and put the email address you'd use to
+send faxes to in a _new line_ called "FaxGate" inside /etc/ax25/axmail.conf.
+When users attempt to send a fax, your account will be hidden from them and
+all they'll see is that they're sending to "a" fax gateway system. 
+
+People have asked about why new incoming mail isn't seen until after the 
+user logs out of axMail. If axMail read directly off of the system 
+mailspool file, then it'd lock out any new incoming mail from being posted 
+to the user's mailbox as it'd have a lock on the spool file, and the 
+message numbers could also possibly change while the user goes to select a 
+message number to read. This would be very confusing to the end user.
+
+If you wish to allow users to use the internet or packet TCP/IP to pop3 
+their mail from your system, they may do so... however keep in mind, any 
+mail they read or list manually within axMail will have it's status 
+changed from "new". As we all know about the pop3 protocol, mail not 
+flagged as "new" isn't popped but it's considered as if the client is 
+using a software package such as eudora or outlook (to name a couple... 
+notice which I listed first? hi!) and they have their options set to leave 
+a copy of their mail on the server. The user will have to log into your 
+node and retrieve their mail from there. After all, isn't part of running 
+packet node services is to encourage hams to actually use their radios to 
+get to such things? :) All you as sysop/root on the box need to do is 
+ensure that a pop3 daemon is installed and running, and that you configure 
+axMail.conf to give the end user proper permissions in their shell to be 
+able to use your pop3 daemon.
+
+I've gone to many days worth of studying how most boxes are configured 
+I've taken it upon myself to try and get axMail as 'bullet proof' and as 
+simple a process as it can possibly be. Unfortunately the program can not 
+read your mind so you'll have to do *some* config work to it... but 
+otherwise it should be a nice low-ram low-resource system for you and your 
+users to enjoy.
+
+Comments and questions are always welcomed!
+
+73 de Brian N1URO
diff --git a/INSTALL b/INSTALL
new file mode 100644
index 0000000..14f70e8
--- /dev/null
+++ b/INSTALL
@@ -0,0 +1,62 @@
+axMail v2.2 - an SMTP mailbox for the various linux node frontends.
+
+Current author: Brian Rogers (N1URO) <n1uro at n1uro.com>
+Past author: Marius Petrescu (YO2LOJ) <mpetrescu at online.ro>
+Creator: Heikki Hannikainen (OH7LZB) <hessu at pspt.fi>
+
+Additional Submissions: Stefano (IW3IJQ) <ziotibia1 at libero.it>
+
+As with any of the softwares I tweek n geek, *use at your own risk*!
+With that said, and the fact that this is GPL software if you find
+something that's borked... don't just submit a bug report. Fix it if
+you can. Rerelease it under your own callsign if you wish, or feel free
+to send me your code and I'll import it in.
+
+This is probably one of the simplest packages to install and configure!
+After you run tar zxvf axmail-0.0.8.tgz cd axmail-0.0.8 (which is where 
+you should be now if you're reading this :) ) and run:
+
+make; make install
+
+(on newer gcc/libs I do know that there's a warning after it makes but
+it doesn't prevent the binary from compiling and so far it seems to test 
+ok. I'll fix that if and when I get the chance but don't hold your breath 
+on it hi!)
+
+cd /usr/local/etc/ax25 and using your favorite editor (vi, joe, pico, etc) and
+edit axmail.conf. In here you can specify how you wish the mailbox
+to handle accounting for end users. On *most* linux systems, the default
+should be "ok" but if you wish to have users contact you first, or if
+you wish to have the system auto-create a standard shell login, or popmail 
+account for the users, etc... you may do so in the file. Double check your 
+settings (it *is* possible you can configure axmail.conf so that everyone 
+has root-group access... but why would you wish to do that? You've been 
+*warned* so double check your config settings for auto-creation of 
+accounts before saving!) The file is well commented to assist you. When 
+you're finished and have become an expert, if you wish to you can delete 
+the comment lines.
+
+You may also customize the file "welcome.txt" in /usr/local/etc/ax25/ if you 
+wish to also. I suggest leaving the first line as-is as this is the so called
+"new user" welcome greeting email. I've supplied a basic and short 
+greeting email message that users will get once they've created their 
+mailbox. If you would rather new users email your mail account directly 
+instead of root, you may wish to change that line.
+
+For the software itself... believe it or not, you're *DONE*! That's all!
+However... now we need to get it hooked into which ever node frontend you 
+run so that users have a way of accessing it. axMail runs as an external 
+process (ExtCmd) to the node. I've tested it with URONode (obviously) and 
+with LinuxNode by Tomi. To do this cd /usr/local/etc/ax25 and using your 
+favorite editor open node.conf and add the following line to your ExtCmds:
+
+ExtCmd          MAil    1       root    /usr/local/sbin/axmail axmail %u
+(note: MA in the word MAil is in CAPS)
+
+Save node.conf and telnet in to test! It should work just fine. Since you 
+would have an existing account on your server, it's unlikely that you'll 
+get the welcome message, but since you can edit it, you'll know what it 
+says :)
+
+Happy mailing!
+
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..a43ea21
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,339 @@
+		    GNU GENERAL PUBLIC LICENSE
+		       Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+                          675 Mass Ave, Cambridge, MA 02139, USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+			    Preamble
+
+  The licenses for most software are designed to take away your
+freedom to share and change it.  By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users.  This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it.  (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.)  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+  To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have.  You must make sure that they, too, receive or can get the
+source code.  And you must show them these terms so they know their
+rights.
+
+  We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+  Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software.  If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+  Finally, any free program is threatened constantly by software
+patents.  We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary.  To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+

+		    GNU GENERAL PUBLIC LICENSE
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+  0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License.  The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language.  (Hereinafter, translation is included without limitation in
+the term "modification".)  Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope.  The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+  1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+  2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+    a) You must cause the modified files to carry prominent notices
+    stating that you changed the files and the date of any change.
+
+    b) You must cause any work that you distribute or publish, that in
+    whole or in part contains or is derived from the Program or any
+    part thereof, to be licensed as a whole at no charge to all third
+    parties under the terms of this License.
+
+    c) If the modified program normally reads commands interactively
+    when run, you must cause it, when started running for such
+    interactive use in the most ordinary way, to print or display an
+    announcement including an appropriate copyright notice and a
+    notice that there is no warranty (or else, saying that you provide
+    a warranty) and that users may redistribute the program under
+    these conditions, and telling the user how to view a copy of this
+    License.  (Exception: if the Program itself is interactive but
+    does not normally print such an announcement, your work based on
+    the Program is not required to print an announcement.)
+

+These requirements apply to the modified work as a whole.  If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works.  But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+  3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+    a) Accompany it with the complete corresponding machine-readable
+    source code, which must be distributed under the terms of Sections
+    1 and 2 above on a medium customarily used for software interchange; or,
+
+    b) Accompany it with a written offer, valid for at least three
+    years, to give any third party, for a charge no more than your
+    cost of physically performing source distribution, a complete
+    machine-readable copy of the corresponding source code, to be
+    distributed under the terms of Sections 1 and 2 above on a medium
+    customarily used for software interchange; or,
+
+    c) Accompany it with the information you received as to the offer
+    to distribute corresponding source code.  (This alternative is
+    allowed only for noncommercial distribution and only if you
+    received the program in object code or executable form with such
+    an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it.  For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable.  However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+

+  4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License.  Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+  5. You are not required to accept this License, since you have not
+signed it.  However, nothing else grants you permission to modify or
+distribute the Program or its derivative works.  These actions are
+prohibited by law if you do not accept this License.  Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+  6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions.  You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+  7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all.  For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices.  Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+

+  8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded.  In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+  9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number.  If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation.  If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+  10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission.  For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this.  Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+			    NO WARRANTY
+
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+		     END OF TERMS AND CONDITIONS
+

+	Appendix: How to Apply These Terms to Your New Programs
+
+  If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+  To do so, attach the following notices to the program.  It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) 19yy  <name of author>
+
+    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., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+    Gnomovision version 69, Copyright (C) 19yy name of author
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License.  Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary.  Here is a sample; alter the names:
+
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+  <signature of Ty Coon>, 1 April 1989
+  Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs.  If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library.  If this is what you want to do, use the GNU Library General
+Public License instead of this License.
diff --git a/Makefile b/Makefile
new file mode 100644
index 0000000..f4b70f5
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,52 @@
+all: axmail
+
+CC = gcc
+LD = gcc
+CFLAGS = -O2 -Wstrict-prototypes -g -I../lib
+LIBS = -lcrypt
+MODULES = utils.o config.o adduser.o command.o mailcmd.o mbox.o head.o lock.o axmail.o quit.o
+
+.c.o:
+	$(CC) $(CFLAGS) -c $<
+
+upgrade: installbin installhelp
+
+install: installbin installconf installhelp
+
+installbin: all
+	install -m 0755 -s -o root -g root axmail	 /usr/local/sbin
+
+installconf:
+	install -m 755    -o root -g root -d		/usr/local/etc/ax25
+	install -m 644    -o root -g root etc/axmail.conf /usr/local/etc/ax25
+	install -m 644    -o root -g root etc/welcome.txt /usr/local/etc/ax25
+
+installhelp:
+	install -m 755    -o root -g root -d		  /usr/local/var/ax25/axmail/help
+	install -m 644    -o root -g root etc/help/*.hlp  /usr/local/var/ax25/axmail/help
+
+back:
+	rm -f ../mail.tar.gz
+	tar cvf ../mail.tar *
+	gzip ../mail.tar
+
+clean:
+	rm -f axmail *.o *~ *.bak core etc/*~ etc/help/*~
+
+distclean: clean
+	rm -f axmail
+
+axmail: $(MODULES)
+	$(LD) -o axmail $(MODULES) $(LIBS) $(LDFLAGS)
+
+utils.o:	utils.h utils.c mbox.h
+config.o:	config.h config.c defines.h axmail.h utils.h
+adduser.o:	adduser.h adduser.c utils.h config.h defines.h
+command.o:	command.h command.c config.h mailcmd.h mbox.h utils.h quit.h
+mailcmd.o:	mailcmd.h mailcmd.c defines.h utils.h mbox.h config.h
+mbox.o:		mbox.h mbox.c utils.h defines.h config.h head.h
+head.o:		head.h head.c defines.h
+utils.o:	utils.h utils.c 
+lock.o:		lock.h lock.c utils.h
+quit.o:		quit.h quit.c config.h lock.h
+axmail.o:	axmail.h axmail.c config.h adduser.h utils.h quit.h mbox.h
diff --git a/README b/README
new file mode 100644
index 0000000..44de3c2
--- /dev/null
+++ b/README
@@ -0,0 +1,374 @@
+axMail - an SMTP mailbox for the various linux node frontends.
+
+PREFACE:
+
+First off, sincere thanks to those who have written to tell me that
+they use axMail, like what I've done to axMail, and for the 
+enthusiasm shown via words and/or code contributions for the program
+in hopes of keeping packet radio networks around the world alive!
+
+INTRO:
+
+Greetings and thanks for taking a look at the program. Below I've posted
+a kind of history of the program to the best of my knowledge taking text
+from existing files. Rather than trying to reinvent the wheel and after
+seeing this program before on Labrat's radio.linux.org.au site, I decided
+to try and give some life into it... partially with the assistance of Phil 
+N1XTB nudging me pretty consistantly for many months in helping him get an 
+SMTP agent in his linux based packet node server without having to install 
+an xNOS overhead node ontop it. :) 
+
+Please do take a moment and read the text based files included with this 
+package so you're a bit familiar with what it does so that you don't get a 
+false perception as to what it can and/or can not do. axMail just might 
+not be what you're looking for or expecting for a node based plugin
+
+CHANGE HISTORY:
+axmail v2.5
+  Updated 30 May, 2015 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- added new delivery receipt function to the send routine. This
+  compliments the read receipt function in the event of high
+  priority mail. Typically the read receipt is an option generated
+  by the recipient who may not decide to generate one. At least this
+  modification ensures with an ESMTP delivery that the sender using
+  axMail will get a reciept from "MAILER-DAEMON" which will verify
+  the status of delivered mail. This change was done in mailcmd.c
+  and is designed with the sendmail binary included with postfix.
+- updated this README file.
+- updated version number in defines.h
+
+axmail v2.4
+  Updated 25 April, 2015 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- cleaned up mbox.c where I had originally placed the receipt checker
+  routine in. This caused loops within the buffer that displayed the
+  message. The true routine lives in mailcmd.c
+- added patch to Makefile provided by Jaroslav at Red Hat for distribution
+  downstream compiles to make packages.
+- changed version in defines.h 
+- major change in command.c, added a new Autofwd command to allow users to
+  auto-forward mail from a remote system to their "home" axMail-FAX base
+  system. Could also be used to forward mail to their internet accounts.
+- added autofwd.hlp file.
+- alphabetized the commandset listing, removed redundantly spelled commands.
+- reworked Makefile and added an "upgrade" option so new files ONLY are
+  deployed after make. Execute using: "make upgrade"
+- updated this file.
+
+axmail v2.3.1 
+  Updated 5 February, 2015 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- added a flag in mailcmd.c where if the request for a receipt exists in a mail
+  message, a bell and a warning sign is generated after the message has been
+  read by the user with instructions to use SR to generate a receipt. This
+  was a difficult routine for me to think of considering the various race
+  conditions that can be expected and met.
+- updated welcome.txt with version upgrade and new feature list.
+- updated README.
+
+axmail v2.3 
+  Updated 5 February, 2015 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- Added a new "Receipt" request flag in mailcmd.c by request of Mitch AB4MW.
+  This defaults to NO but when flagged to YES, a request will be sent to the
+  remote client's agent. If the agent supports such, they will be prompted
+  whether or not to honor your receipt request. This is history as NO AGENT
+  FOR PACKET TERMINALS SUPPORTS THIS! The function of a generated read 
+  receipt is similar to how HylaFax generates confirmation of transmission
+  receipt mails to your mailbox. Currently mail read in axMail will NOT
+  generate a receipt back. I may work on this later, but for now it doesn't
+  exist.
+* My thoughts of the receipt function is negative. The fact that I may be
+  sending notification that I'm in my email client to a remote destination
+  IMHO is such that a webcam may as well be turned on and watch me do email,
+  and send the stream to "Big Brother" and I don't mean the television show.
+  </rant>
+- Updated defines.h with the new version number.
+- Updated welcome.txt so the new version number is displayed.
+
+axmail v2.2 
+  Updated 25 December, 2014 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- Made some maintenance changes, but forgot to log them in here.
+axmail v2.1.1
+ Updated 30 October, 2014 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- Makefile
+  Code provided by Bob Tenty VE3TOK to make it more compatable
+  with newer GCC compiler requirements.
+- utils.c
+  Code provided by Bob Tenty VE3TOK to fix a warning produced when
+  compiling.
+- defines.h
+  Changed version number to reflect the changes incorporated by 
+  Bob Tenty VE3TOK and committed to the subversion repository.
+
+axmail v2.1
+ Updated 31 July, 2014 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- axmail.c
+  Code provided by Jaroslov OK2JRQ fixes a potential security hole in
+  the system privilege matching.
+- global
+  axMail is now under review for considerations as standard packaging in
+  RedHat's fedora project. It appears it's going to be added as a package.
+
+axmail v2.0
+  Updated 8 July, 2013 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- defines.h
+  Updated version number to reflect version release 2.0. Version 1.0.5
+  was simply a maintenance test package to try and reincorporate what
+  I had done up to version 1.0.6 which I believe was one of my last
+  releases up to 2009. Since I've done all that I can recall at this
+  point and time, I decided to match URONode's release numerics with
+  a 2.0 release version.
+
+axmail v1.0.5
+  Updated 5 July, 2013 by Brian Rogers (N1URO) <n1uro at n1uro.net>
+Changes:
+- defines.h
+  Updated email listings to reflect the most current ones I could find
+  including my own. Also added 2013 to the years worked on axMail by
+  me.
+
+- quit.c
+  Forced ALL mail, read or otherwise when user quits to save to the
+  user's system mailbox. This is for reverse compatability with those
+  who may also run a web-based email service on the internet such as
+  NeoMail, EMUMail, etc. Prior, the system was supposed to separate
+  any read mail (and all accompanying mail in that session) to the
+  axmail ~/mbox file. We don't want this for the specific reason of
+  "reverse email client" compatability.
+
+axmail v1.0.4
+  Updated 23 May, 2008 by Brian Rogers (N1URO) <brian at support.uroweb.net>
+ Changes:
+- setpwnam.c
+  Changed the way SIGPIPE was handled. Instead of being ignored, it will
+  now read a SIGQUIT properly if a QUIT is signaled to axmail either via
+  a shell prompt, or a node frontend. I've been noticing especially on
+  some timeouts that temp files don't flush as they should and the
+  user's directory can start to fill up.
+
+axMail v1.0.3
+  Updated 2 December, 2007 by Brian Rogers (N1URO) <brian at support.uroweb.net>
+Changes:
+- mailcmd.c
+  Reset the way I wanted to handle the user input routine for sending faxes.
+  Commented out some more unneeded/unused code in the do_fax routine... will
+  clean it up in next release or so.
+
+- mailcmd.c
+  cleaned up a bug I introduced in the never released 1.0.2 where the
+  X-Mailer was duping itself after each line of the body of a message.
+
+- sfax.hlp
+  Reworded the SFax help file to help show some examples of how to format
+  the header. 
+
+axMail v1.0.2
+  Updated 24 November, 2007 by Brian Rogers (N1URO) <brian at support.uroweb.net>
+Changes:
+- mailcmd.c
+  Cleaned up some of the code in SFax. Also made some cosmetic changes.
+
+axMail v1.0.1
+  Updated 31 October, 2007 by Brian Rogers (N1URO) <brian at support.uroweb.net>
+Changes:
+- mailcmd.c
+  Added a new routine to allow users to send faxes. This is defined by the
+  command "SF" for Send Fax. The routine was taken from the "S"end function
+  however since it's a one-way transmission, there is no reply available
+  nor is there an option for users to fax to any fax service as some I know
+  are pay services.
+- config.h
+  added definitions for faxgate in axmail.conf
+- config.c
+  added routine to allow for faxgate as a variable and be called from 
+  mailcmd.c
+- defines.h
+  version upgraded from v1.0.0 (unreleased - test version) to
+  v1.0.1
+- etc/axmail.conf
+  Added new line called "FaxGate" with an example of how to properly
+  configure this line.
+- etc/help/sfax.hlp
+  Added new file "sfax.hlp" which is an online help file for the SFax
+  command.
+
+axMail v0.0.9
+  Updated 26 September, 2006 by Brian Rogers (N1URO) <n1uro at n1uro.com>
+Changes:
+- mailcmd.c
+  Added a new routine that prompts the sender whether or not the message
+  is of an emergency/high priority mail message. If it's emergency message
+  then the headers are appended with an X-code flagged in such a manner
+  that Eudora and Outlook will display the received mail with a red flag
+  of sorts. The idea of such came to me in thinking of "what can I do
+  to help improve means of emergency communications using TCP/IP, Linux,
+  and packet radio?" Having the ability to "red flag" an SMTP message
+  I don't believe has yet to be available in any packet messaging
+  system... axMail I hope is the first.
+
+  If a user just hits enter, or selects "no" then the mail message
+  is sent under normal send routines.
+
+  found a minor bug in my routine where if an end user answered
+  "yes" in wanting to send an emergency/high priority message the system
+  ignored the request and sent it as 'normal' delivery. Made a minor
+  change to bullet-proof the responce.
+
+  Added online help text if user is unsure about sending a message
+  flagged urgent or normal. This text is available when the user is
+  prompted for priority selection by hitting "?" at the prompt.
+
+- defines.h
+  Version updated from v0.0.8 to v0.0.9
+
+axMail v0.0.8
+  Updated 2006 by Brian Rogers (N1URO) <n1uro at n1uro.com>
+ 
+Changes:
+ - mailcmd.c
+   Rewrote and incorporated code provided by IW3IJQ how axMail inserts
+   it's version number in the X-Mailer: string.
+ - mailcmd.c   
+   Added an X-Origin: string to show those peeking at mail headers
+   just how the message was possibly sent... by AMATEUR RADIO!
+ - axmail.conf
+   Added config option in "AllowMail" for axhome, a rewrite of code
+   submitted by Stefano IW3IJQ. While I stripped out home directory
+   structures similar to that of qmail or axspawn, Stefano convinced
+   me that it may be easier to manage home directories for axMail users
+   who don't have shell access to branch out within a preset directory.
+ - defines.h
+   Updated version number from 0.0.7 to 0.0.8
+
+ - axmail.c and config.c
+   Rewrote and incorporated code to allow for the routines to use
+   what Stefano IW3IJQ originally labled "newuhome" to use "axhome".
+   While I was at it, I rewrote and shortened the error text pushed
+   to a user who doesn't have permission to use such a directory.
+
+ * Note: When I write error texts and menus, I try to write them for
+   users on a multi-hop 1200 baud path thus the shorter the better as
+   long as context isn't lost and for long distance hops where full
+   paclen may cause retries (worse yet timeouts!)
+
+axMail v0.0.7
+  
+  Updated 2005 by Brian Rogers (N1URO) <n1uro at n1uro.com>
+
+Changes:
+ - cosmetics
+   My usual "I like seeing this this way" type cosmetics... too many
+   to mention!
+
+ - adduser.c
+   changed the hard coding of user 'home' directories so that instead
+   of them going into a period delimited sort, just dump em all into
+   /home/<user> which seems to be "the norm" on most systems I've had
+   to assist with.
+
+ - adduser.c
+   fixed a bug where creating a user was actually causing the program to
+   segfault upon exit the first time a user went into the mailbox! The
+   node frontends hid this segfault as the program still flushed itself
+   from ram but I spotted it when running it at a command prompt. The
+   segfault came when axMail attempted to write mail back to the user's
+   system mailbox and it didn't exist. How I fixed this is listed next.
+   This may just be a new bug that appeared with the upgrading of libs,
+   this I'm unsure of and since I have no desire to go backwards I have
+   decided to actually make a minor routine...
+
+ - welcome.txt
+   New users are now sent a "welcome" message that the sysop can easily
+   customize to their desires. It's located at /etc/ax25/welcome.txt.
+   I figured that since axMail was segfaulting because such a file did
+   not exist, I might as well make use of this need by having the program
+   send the user a greeting.   
+
+ - defines.h
+   Changed paths to be more in line with the more modern type configs
+   as a default. Paths can still be defined by the sysop prior to 
+   compiling axMail. 
+
+ - Makefile
+   I changed the default of make install to include all of the subroutines
+   within the Makefile yet leaving such things as "make installbin" 
+   available as runtime options if just a binary refresh creation is 
+   desired. 
+
+ - other
+   I'm sure I missed a note or two *shrug*
+
+axMail v0.0.6
+
+  Tweeks made by Marius Petrescu (?) I know there was a ver 0.0.6 which
+  I at one time had but lost and can't seem to find it. My (n1uro) 
+  changes may have alread been incorporated.
+
+axMail v0.0.5
+
+  True mailbox functionalities created by Marius Petrescu.
+  Added Mailbox save routines (compatible with the command line
+  mail agent, including ~/mbox file)
+
+axMail v0.0.4
+
+  Copyright (c) 1996 Heikki Hannikainen (OH7LZB) <hessu at pspt.fi>
+  
+    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., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+
+  Don't give this one to anyone yet... it is NOT ready for distribution!
+
+  This is a simple mail user agent intended to provide the
+mail functions in xNOS in a Linux ax.25 environment. If required,
+it creates a normal user account for each new user (code mostly taken
+from axspawn by Joerg Reuter (DL1BKE)), so that they can receive mail
+on the system. axMail uses sendmail (or similar) to deliver mail, and
+reads mail from each user's system mailbox (/var/spool/mail/username).
+It does not provide any means of transferring mail between hosts.
+
+  axMail provides a simple, low-overhead user interface, much similar
+to /bin/mail, xNOS and the packet BBS systems. It's useful for providing 
+good SMTP mail services for "dumb" ax.25 users over slow radio channels.
+
+  axMail is intended to be called from node. It takes one command
+line argument of the user's callsign (with or without SSID). It must
+be run as root, but it setuid()'s itself to the respective user's
+privileges as soon as possible. It might run from ax25d as well.
+It can also be executed from a shell with user privileges.
+
+  Some code (command parser, configuration file stuff) and the internal 
+architecture was taken from the LinuxNode frontend by Tomi Manninen 
+(OH2BNS). Thanks!
+
+INSTALLATION:
+
+	See the file: INSTALL
+
+TODO:
+  I know I can clean up the code a LOT more, will do so for a maintenance
+  release which will most likely be v1.0.2.
+
+	Suggestions?
+
+-- 
+Brian Rogers <n1uro at n1uro.net> [n1uro at n1uro.#cct.ct.usa.noam]
+ftp://ftp.n1uro.net/packet
diff --git a/UPGRADING b/UPGRADING
new file mode 100644
index 0000000..fc17377
--- /dev/null
+++ b/UPGRADING
@@ -0,0 +1,6 @@
+If you are upgrading axmail from ver 1.0.1, all you really need to do
+is copy the binary over the existing one.
+
+If you are upgrading axMail from any version equal to or earlier than 1.0.0
+back up your /etc/ax25/axmail.conf file and do a full install.
+
diff --git a/adduser.c b/adduser.c
new file mode 100644
index 0000000..0519fb8
--- /dev/null
+++ b/adduser.c
@@ -0,0 +1,193 @@
+
+/* adduser.c - create an user account (yecch) */
+ 
+#include <stdio.h>
+#include <stdlib.h>
+#include <strings.h>
+#include <pwd.h>
+#include <unistd.h>
+#include <sys/stat.h>
+#include <sys/file.h>
+#include <errno.h>
+#include <crypt.h>
+#include <string.h>
+
+#include "adduser.h"
+#include "utils.h"
+#include "config.h"
+#include "defines.h"
+
+/* Ask for a new password, and keep it sane */
+
+void get_passwd(char *newuser, char *passw)
+{
+	char passi[12];
+
+repass: /* Get password */
+	getstr(passi, 10, "Enter password for the new account (6-8 characters, ? for help): ");
+
+	if (!strcmp(passi, "?")) {
+		printf("Your password must be 6 to 8 characters long, and it may not be the same as\n");
+		printf("your login name (in this case, your callsign).\n");
+		goto repass;
+	}
+	if ((strlen(passi) > 8) || (strlen(passi) < 6)) {
+		printf("Password must be 6-8 characters long.\n");
+		goto repass;
+	}
+	if (!strcasecmp(passi, newuser)) {
+		printf("Password may not be your login name (callsign).\n");
+		goto repass;
+	}
+
+	/* Crypt password */
+	strcpy(passw, crypt(passi, "ax")); /* Okay, salt _should_ be random... */
+}
+
+/* add a new user to /etc/passwd and do some init */
+
+int new_user(char *newuser)
+{
+	struct passwd pw, *pwp;
+	uid_t uid;
+	FILE *fp;
+	char homedir[256], userdir[256];
+	char buf[4096];
+	char subdir[4];
+	char passw[20];
+	char str[LINESIZE + 1];
+	int cnt = 0;
+	unsigned char *p, *q;
+	struct stat fst;
+	int fd_a, fd_b, fd_l;
+	
+	/* Build path for home directory */
+
+	strncpy(subdir, newuser, 3);
+	subdir[3] = '\0';
+	sprintf(homedir, "%s/%s", def_homedir, newuser);
+	strcpy(userdir, homedir);
+
+	getname(fullname);
+
+	if (strlen(fullname) == 0) {
+		printf("Okay, using your callsign as your name. You may change it later.\n");
+		strcpy(fullname, newuser);
+	}
+
+	/* Get password */
+
+	switch (login_allowed)	{
+		case 0:	strcpy(passw, "*");
+			break;
+		case 1: get_passwd(newuser, passw);
+			break;
+		case 2: strcpy(passw, ""); /* Yuck! */
+			break;
+	}
+	
+	/* Lock */
+	fd_l = open(LOCK_AXMAIL_FILE, O_CREAT | O_APPEND, S_IRUSR | S_IWUSR);
+	flock(fd_l, LOCK_EX);
+
+retry:
+	/* Find first free UID */
+	cnt++;
+
+	for (uid = first_uid; uid < 65535; uid++)
+	{
+		pwp = getpwuid(uid);
+		if (pwp == NULL)
+			break;
+	}
+
+	if (uid >= 65535 || uid < first_uid)
+		return -1;
+
+	/* build directories for home */
+
+	p = homedir;
+		
+	while (*p == '/') p++;
+
+	chdir("/");
+
+	while(p)
+	{
+		q = strchr(p, '/');
+		if (q)
+		{
+			*q = '\0';
+			q++;
+			while (*q == '/') q++;
+			if (*q == 0) q = NULL;
+		}
+
+		if (stat(p, &fst) < 0)
+		{
+			if (errno == ENOENT)
+			{
+				mkdir(p, S_IRUSR|S_IWUSR|S_IXUSR|S_IRGRP|S_IWGRP|S_IXGRP|S_IROTH|S_IWOTH|S_IXOTH);
+
+				if (q == NULL)
+				{
+					chown(p, uid, user_gid);
+					chmod(p, S_IRUSR|S_IWUSR|S_IXUSR);
+				} 
+			}
+			else
+				return -1;
+		}
+		
+		if (chdir(p) < 0)
+			return -1;
+		p = q;
+	}
+
+	/* Add the user now */
+
+	fp = fopen(PASSWDFILE, "a+");
+	if (fp == NULL)
+		return -1;
+	
+	pw.pw_name   = newuser;
+	pw.pw_passwd = passw;
+	pw.pw_uid    = uid;
+	pw.pw_gid    = user_gid;
+	pw.pw_gecos  = fullname;
+	pw.pw_dir    = userdir;
+	pw.pw_shell  = def_shell;
+
+	if ((getpwuid(uid) != NULL) && (cnt <= 10)) goto retry; /* oops?! */
+
+	if ((putpwent(&pw, fp) < 0) || (cnt > 10))
+		return -1;
+
+	flock(fd_l, LOCK_UN);
+	fclose(fp);
+
+	/* Copy ax25.profile */
+	
+	fd_a = open(CONF_AXMAIL_PROF_FILE, O_RDONLY);
+	
+	if (fd_a > 0)
+	{
+		fd_b = open(USERPROFILE, O_CREAT|O_WRONLY, S_IRUSR|S_IWUSR|S_IXUSR);
+
+		if (fd_b < 0)
+			return -1;
+		
+		while ( (cnt = read(fd_a, &buf, sizeof(buf))) > 0 )
+			write(fd_b, &buf, cnt);
+		close(fd_b);
+		close(fd_a);
+		chown(USERPROFILE, uid, user_gid);
+	
+	}
+/* Be nice and send the new user a welcome message :) */
+
+	sprintf(str, "%s -oem %s@%s < %s", BIN_AXMAIL_SENDMAIL, newuser, hostname, WELCOME);
+                system(str);
+	return 0;
+}
+
diff --git a/adduser.h b/adduser.h
new file mode 100644
index 0000000..ef0effd
--- /dev/null
+++ b/adduser.h
@@ -0,0 +1,2 @@
+
+extern int new_user(char *newuser);
diff --git a/axmail.c b/axmail.c
new file mode 100644
index 0000000..1fd716c
--- /dev/null
+++ b/axmail.c
@@ -0,0 +1,297 @@
+/* axmail.c - The command parser and main function */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <ctype.h>
+#include <unistd.h>
+#include <signal.h>
+#include <time.h>
+#include <syslog.h>
+#include <pwd.h>
+#include <crypt.h>
+#include <error.h>
+
+#include "config.h"
+#include "axmail.h"
+#include "utils.h"
+#include "adduser.h"
+#include "quit.h"
+#include "mbox.h"
+
+/* Parse c-style escapes (neat to have!) */
+ 
+static char *parse_string(char *str)
+{
+	char *cp = str;
+	unsigned long num;
+
+	while (*str != '\0' && *str != '\"') {
+		if (*str == '\\') {
+			str++;
+			switch (*str++) {
+			case 'n':
+				*cp++ = '\n';
+				break;
+			case 't':
+				*cp++ = '\t';
+				break;
+			case 'v':
+				*cp++ = '\v';
+				break;
+			case 'b':
+				*cp++ = '\b';
+				break;
+			case 'r':
+				*cp++ = '\r';
+				break;
+			case 'f':
+				*cp++ = '\f';
+				break;
+			case 'a':
+				*cp++ = '\007';
+				break;
+			case '\\':
+				*cp++ = '\\';
+				break;
+			case '\"':
+				*cp++ = '\"';
+				break;
+			case 'x':
+				num = strtoul(--str, &str, 16);
+				*cp++ = (char) num;
+				break;
+			case '0':
+			case '1':
+			case '2':
+			case '3':
+			case '4':
+			case '5':
+			case '6':
+			case '7':
+				num = strtoul(--str, &str, 8);
+				*cp++ = (char) num;
+				break;
+			case '\0':
+				return NULL;
+			default:
+				*cp++ = *(str - 1);
+				break;
+			};
+		} else {
+			*cp++ = *str++;
+		}
+	}
+	if (*str == '\"')
+		str++;		/* skip final quote */
+	*cp = '\0';		/* terminate string */
+	return str;
+}
+
+/* Parse command line to argv, honoring quotes and such */
+ 
+int parse_args(char *argv[],char *cmd)
+{
+	int ct = 0;
+	int quoted;
+
+	while (ct < 31)
+	{
+		quoted = 0;
+		while (*cmd && isspace(*cmd))
+			cmd++;
+		if (*cmd == 0)
+			break;
+		if (*cmd == '"') {
+			quoted++;
+			cmd++;
+		}
+		argv[ct++] = cmd;
+		if (quoted) {
+			if ((cmd = parse_string(cmd)) == NULL)
+				return 0;
+		} else {
+			while (*cmd && !isspace(*cmd))
+				cmd++;
+		}
+		if (*cmd)
+			*cmd++ = 0;
+	}
+	argv[ct] = NULL;
+	return ct;
+}
+
+/* Find the command from the command table and execute it. */
+ 
+int cmdparse(struct cmd *cmds, char *cmdline)
+{
+	struct cmd *cmdp;
+	int argc;
+	char *argv[32];
+
+	if ((argc = parse_args(argv, cmdline)) == 0 || *argv[0] == '#')
+		return 0;
+	strlwr(argv[0]);
+	for (cmdp = cmds; cmdp->function != NULL; cmdp++)
+		if (strncasecmp(cmdp->name, argv[0], strlen(argv[0])) == 0)
+			break;
+	if (cmdp->function == NULL)
+		return -1;
+	return (*cmdp->function)(argc, argv);
+}
+
+/* Signal handlers (which don't do all the things they SHOULD do) */
+
+static void alarm_handler(int sig)
+{
+	printf("\nTimeout! Closing...\n");
+	exit(1);
+}
+
+static void term_handler(int sig)
+{
+	printf("System going down! Closing...\n");
+	exit(1);
+}
+
+/* Initialisation for the user */
+ 
+int init_user(char *call)
+{
+	struct passwd *pw;
+	char pass[13], salt[3];
+	char *p;
+	char axhome[64];
+
+	/* Strip SSID */
+	if (local) {
+		pw = getpwuid(getuid());
+	} else {
+		strcpy(callsign, call);
+		strcpy(username, callsign);
+		strlwr(username);
+		p = strchr(username, '-');
+		if (p) *p = '\0';
+		pw = getpwnam(username);
+	}
+
+	if (!pw) {
+		if (local)
+			panic("Ouch, you don't seem to be in the password file.\n");
+		if (autocreate) {
+			syslog(LOG_NOTICE, "Adding new user %s", username);
+			if (new_user(username) < 0) {
+				syslog(LOG_NOTICE, "Could not add new user %s", username);
+				printf("Sorry, could not add new user.\n");
+				return -1;
+			}
+			printf("You have been added to the user list of %s.\nWelcome.\n", hostname);
+			pw = getpwnam(username);
+		} else {
+			syslog(LOG_NOTICE, "New user %s not accepted", username);
+			printf("Sorry, new users are not accepted at this time.\n");
+			return -1;
+		}
+	} else {
+		if (local) {
+			strcpy(username, pw->pw_name);
+			strcpy(callsign, username);
+		}
+		/* Strip full name from the gecos field... */
+		if (strchr(pw->pw_gecos, ',') == NULL)
+			strcpy(fullname, pw->pw_gecos);
+		else
+			strcpy(fullname, strtok(pw->pw_gecos, ","));
+	}
+	
+	if (!local) {
+		if ((mail_allowed == 1) && (strcmp(pw->pw_passwd, "*"))) {
+			printf("Sorry, you are not allowed to use axmail (you have a password set).\n");
+			return -1;
+		}
+		
+		if ((mail_allowed == 2) && (!strcmp(pw->pw_passwd, "*"))) {
+			printf("Sorry, you are not allowed to use axmail (locked out in password file).\n");
+			return -1;
+		}
+		if (mail_allowed == 3) {
+			sprintf(axhome, "%s/%s", def_homedir, username);
+			if (strcmp(pw->pw_dir, axhome)) {
+				printf("Sorry, you are not allowed to use axmail - bad axhome.\n");
+				return -1;
+			}
+		}
+		
+		if (identification == 1) {
+			getstr(pass, 12, "Password: ");
+			strncpy(salt, pw->pw_passwd, 2);
+			salt[2] = '\0';
+			if (strcmp(pw->pw_passwd, (char *)crypt(pass, salt))) {
+				printf("Login incorrect.\n");
+				return -1;
+			}
+		}
+
+/* code supplied by Jaroslav Skarvada */
+		if ( (setgroups(0, NULL) == -1) || (setgid(pw->pw_gid) == -1) || (setuid(pw->pw_uid) == -1) )
+			panic("init_user: Argh, cannot setuid() or setgid() to %i.%i", pw->pw_uid, pw->pw_gid);
+	}
+	
+	homedir = strdup(pw->pw_dir);
+	return 0;
+}
+
+int main(int argc, char **argv)
+{
+	char *p;
+
+	signal(SIGALRM, alarm_handler);
+	signal(SIGTERM, term_handler);
+        openlog("axmail", LOG_PID, LOG_DAEMON);
+
+	if (getuid() != 0)
+		local = 1;	/* Hey, we're being executed by a "normal"
+				 * user, with user privileges! 
+				 */
+	
+	if ((!local) && (argc != 2)) {
+		printf("axmail: Callsign not found as a parameter.\n");
+		syslog(LOG_NOTICE, "Callsign not found as a parameter\n");
+		return 1;
+	}
+	
+	if (read_config() == -1) /* Read axmail.conf */
+		return 1;
+		
+	printf("%s\n", VERSION);
+	
+	if (init_user(argv[1]) == -1) /* Get user specific data, create user account */
+		return 1;
+		
+	tinit();	/* Filenames etc */
+	getmail();	/* Scan mailbox */
+	
+	if ((newm) || (messages))
+		printf("You have %i messages (%i new).\n", messages, newm);
+		
+	prompt();
+	fflush(stdout);
+	
+	p = malloc(1024);
+	
+	while (1)
+	{
+		fgets(p, 1023, stdin);
+
+		if (p == NULL)
+                	quit(0, 0);
+                	
+		if (cmdparse(Mailcmds, p) == -1)
+			printf("Unknown command. Type ? for a list.\n");
+		
+		prompt();
+		fflush(stdout);
+	}
+	
+}
+
diff --git a/axmail.h b/axmail.h
new file mode 100644
index 0000000..1a57bdc
--- /dev/null
+++ b/axmail.h
@@ -0,0 +1,4 @@
+
+extern int parse_args(char *argv[],char *cmd);
+extern int cmdparse(struct cmd *cmds, char *cmdline);
+
diff --git a/command.c b/command.c
new file mode 100644
index 0000000..0e9dd4b
--- /dev/null
+++ b/command.c
@@ -0,0 +1,148 @@
+/* command.c - Commands which have nothing to do with mail... */
+
+#include <stdio.h>
+#include <string.h>
+#include <ctype.h>
+#include <unistd.h>
+#include <time.h>
+
+#include "defines.h"
+#include "command.h"
+#include "config.h"
+#include "mailcmd.h"
+#include "mbox.h"
+#include "utils.h"
+#include "quit.h"
+
+struct cmd Mailcmds[] = {
+	{ "?",		do_help		},
+	{ "Autofwd",	do_forward	},
+	{ "Bye",	do_exit		},
+	{ "Cancel",	do_quit		},
+	{ "Delete",	do_kill		},
+	{ "Exit",	do_exit		},
+	{ "Help",	do_help		},
+	{ "Info",	do_help		},
+	{ "Kill",	do_kill		},
+	{ "List",	do_list		},
+	{ "Name",	do_name		},
+	{ "Quit",	do_exit		},
+	{ "Read",	do_read		},
+	{ "Send",	do_send		},
+	{ "SFax",	do_fax		},
+	{ "SReply",	do_send		},
+	{ "STatus",	do_status	},
+	{ "Unkill",	do_unkill	},
+	{ "Verbose",	do_read		},
+	{ NULL,		NULL		}
+};
+
+int do_status(int argc, char **argv)
+{
+	printf("Messages: %i\n", messages);
+	return 0;
+
+}
+
+int do_name(int argc, char **argv)
+{
+	char name[32];
+	
+	getname(name);
+	
+	if (strlen(name) == 0)
+		printf("Name not changed. ");
+	else {	/* Okay, save it */
+		strcpy(fullname, name);
+	}
+	
+	printf("You're now known as %s.\n", fullname);
+	
+	return 0;
+}
+
+/* int do_forward(int argc, char **argv) */
+int do_forward(int argc, char **argv)
+{
+	char *email;
+	char *fwdfile;
+	char fwd[79];
+	char forward[79];
+
+	getaddy(fwd);
+	FILE *fptr;
+
+	sprintf(forward, "%s/.forward", homedir);
+	fwdfile = strdup(forward);
+	fptr = fopen(fwdfile, "w+");
+        
+//        if (strlen(fwd) == 0);
+//                printf("Auto Forwarding stopped.\n");
+//        else  { /* Okay, save it */
+                fprintf(fptr, "%s", fwd);
+//        }
+        
+        printf("You're mail will be sent to:\n%s\nThank you.\n", fwd);
+        fclose(fptr); 
+        return 0;
+}
+
+int do_help(int argc, char **argv)
+{
+	FILE *fp;
+	char fname[80], line[256];
+	struct cmd *cmdp;
+	int i = 0;
+
+	if (*argv[0] == '?') {				/* "?"		*/
+		printf("Commands:\n");
+		for (cmdp = Mailcmds; cmdp->name != NULL; cmdp++) {
+			printf("%s%s", i ? ", " : "", cmdp->name);
+			if (++i == 10) {
+				printf("\n");
+				i = 0;
+			}
+		}
+		if (i) printf("\n");
+		return 0;
+	}
+	strcpy(fname, DATA_AXMAIL_HELP_DIR);
+	if (*argv[0] == 'i') {				/* "info"	*/
+		strcat(fname, "info.hlp");
+		printf("%s - %s\n", VERSION, COPYRIGHT);
+		printf("%s", LICENSE);
+	} else if (argc == 1) {				/* "help"	*/
+		strcat(fname, "help.hlp");
+	} else {					/* "help <cmd>"	*/
+		if (strchr(argv[1], '/') == NULL) {
+			strlwr(argv[1]);
+			strcat(fname, argv[1]);
+			strcat(fname, ".hlp");
+		}
+	}
+	if ((fp = fopen(fname, "r")) == NULL) {
+		if (*argv[0] != 'i')
+			printf("No help for command %s.\n", argv[1] ? argv[1] : "help");
+		return 0;
+	}
+	if (*argv[0] != 'i')
+		printf("Help for command %s:\n", argv[1] ? argv[1] : "help");
+	while (fgets(line, 256, fp) != NULL) {
+		printf("%s", line);
+		}
+	fclose(fp);
+	return 0;
+}
+
+int do_quit(int argc, char **argv)
+{
+	quit(0, 0);
+	return 0;
+}
+
+int do_exit(int argc, char **argv)
+{
+	quit(1, 0);
+	return 0;
+}
+
diff --git a/command.h b/command.h
new file mode 100644
index 0000000..a47486b
--- /dev/null
+++ b/command.h
@@ -0,0 +1,9 @@
+
+/* in command.c */
+extern int do_status(int argc, char **argv);
+extern int do_name(int argc, char **argv);
+extern int do_help(int argc, char **argv);
+extern int do_quit(int argc, char **argv);
+extern int do_exit(int argc, char **argv);
+extern int do_forward(int argc, char **argv); 
+/* extern int do_forward(void); */
diff --git a/config.c b/config.c
new file mode 100644
index 0000000..6790261
--- /dev/null
+++ b/config.c
@@ -0,0 +1,285 @@
+
+/* config.c - read configuration */
+  
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <ctype.h>
+#include <pwd.h>
+#include <grp.h>
+#include <utmp.h>
+#include <unistd.h>
+#include <sys/stat.h>
+
+#include "config.h"
+#include "defines.h"
+#include "axmail.h"
+#include "utils.h"
+
+char callsign[20];
+char username[20];
+char fullname[31];
+char *homedir;			/* User's home directory */
+char *maildir;			/* User's mail directory (~/mail) */
+char *mailbox;			/* System mailbox (/var/spool/mail/user) */
+char *userbox;			/* User's mailbox (~/mbox) */
+char *mailconf;			/* User's own axmail configuration */
+
+int local = 0;			/* Running with user privileges? */
+
+char *tempMail; 		/* Temporary files: ~/mail/ax?(-pid-) */
+char *tempNewMail;		/* Temporary files: ~/mail/axnew?(-pid-) */
+char *tempEdit;
+char *tempMesg;
+char *tempRcpt;
+
+char *hostname		= NULL;
+char *def_shell		= NULL;
+char *def_homedir	= NULL;
+char *faxgate		= NULL;
+
+int mail_allowed	= 0;
+int identification	= 0;
+
+int autocreate 		= FALSE;
+int login_allowed	= FALSE;
+int first_uid		= 400;
+int last_uid		= 65535;
+gid_t user_gid		= 0;
+
+long IdleTimeout	= 900L;		/* default to 15 mins */
+
+static int do_allowmail(int, char **);
+static int do_autocreate(int, char **);
+static int do_autogroup(int, char **);
+static int do_first_uid(int, char **);
+static int do_homedir(int, char **);
+static int do_faxgate(int, char **);
+static int do_hostname(int, char **);
+static int do_identification(int, char **);
+static int do_idletimeout(int, char **);
+static int do_loginallowed(int, char **);
+static int do_last_uid(int, char **);
+static int do_shell(int, char **);
+
+static struct cmd cfg_cmds[] = {
+	{ "allowmail",		do_allowmail	},
+	{ "autocreate",		do_autocreate	},
+	{ "autogroup",		do_autogroup	},
+	{ "faxgate",		do_faxgate	},
+	{ "first_uid",		do_first_uid	},
+	{ "homedir",		do_homedir	},
+	{ "hostname",		do_hostname	},
+	{ "identification",	do_identification	},
+	{ "idletimeout",	do_idletimeout	},
+	{ "loginallowed",	do_loginallowed	},
+	{ "last_uid",		do_last_uid	},
+	{ "shell",		do_shell	},
+	{ NULL,			NULL		}
+};
+
+/* ***************************************************************** */
+
+static int do_allowmail(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	if (!strcasecmp(argv[1], "all"))
+		mail_allowed = 0;
+	else if (!strcasecmp(argv[1], "nologin"))
+		mail_allowed = 1;
+	else if (!strcasecmp(argv[1], "passwd"))
+		mail_allowed = 2;
+	else if (!strcasecmp(argv[1], "axhome"))
+		mail_allowed = 3;
+	else
+		return -1;
+	return 0;
+}
+
+static int do_autocreate(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	if (!strcasecmp(argv[1], "yes"))
+		autocreate = 1;
+	else
+		autocreate = 0;
+	return 0;
+}
+
+static int do_autogroup(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+
+	user_gid = atoi(argv[1]);
+
+        if (user_gid == 0) {
+		struct group * gp = getgrnam(argv[1]);
+		if (gp != NULL)
+			user_gid = gp->gr_gid;
+		else {
+			printf("Group %s not found.\n", argv[1]);
+			return -1;
+		}
+		endgrent();
+	}
+
+	if (user_gid == 0) {
+		printf("Default GID for new users must be set and non-zero.\n");
+		return -1;
+	}
+	return 0;
+}
+
+static int do_faxgate(int argc, char **argv)
+{
+	        if (argc < 2)
+			                return -1;
+		        faxgate = strdup(argv[1]);
+			        return 0;
+}
+
+static int do_first_uid(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	first_uid = atoi(argv[1]);
+	return 0;
+}
+
+static int do_last_uid(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	last_uid = atol(argv[1]);
+	return 0;
+}
+
+static int do_idletimeout(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	IdleTimeout = atol(argv[1]);
+	return 0;
+}
+
+static int do_homedir(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	def_homedir = strdup(argv[1]);
+	return 0;
+}
+
+static int do_hostname(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	hostname = strdup(argv[1]);
+	return 0;
+}
+
+static int do_identification(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	if (!strcasecmp(argv[1], "none"))
+		identification = 0;
+	else if (!strcasecmp(argv[1], "passwd"))
+		identification = 1;
+	else
+		return -1;
+	return 0;
+}
+
+static int do_loginallowed(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	if (!strcasecmp(argv[1], "yes"))
+		login_allowed = 1;
+	else if (!strcasecmp(argv[1], "crazy"))
+			login_allowed = 2;
+		else
+			login_allowed = 0;
+	return 0;
+}
+
+static int do_shell(int argc, char **argv)
+{
+	if (argc < 2)
+		return -1;
+	def_shell = strdup(argv[1]);
+	return 0;
+}
+
+/* ***************************************************************** */
+
+/* Set the temporary file names, paths and such, and make sure
+   they're available for us to use... */
+
+void tinit(void)
+{
+	int pid;
+	char pat[PATHSIZE];
+	struct stat fst;
+
+	umask(077);
+	pid = getpid();
+		
+	sprintf(pat, "%s/mail", homedir);
+	maildir = strdup(pat);
+	
+	sprintf(pat, "%s/axM%05d", maildir, pid);
+	tempMail = strdup(pat);
+	sprintf(pat, "%s/axnewM%05d", maildir, pid);
+	tempNewMail = strdup(pat);
+	sprintf(pat, "%s/axE%05d", maildir, pid);
+	tempEdit = strdup(pat);
+	sprintf(pat, "%s/axT%05d", maildir, pid);
+	tempMesg = strdup(pat);
+	
+	sprintf(pat, "%s/mbox", homedir);
+	userbox = strdup(pat);
+	
+	sprintf(pat, "%s%s", DATA_AXMAIL_MAIL_DIR, username);
+	mailbox = strdup(pat);
+	
+	sprintf(pat, "%s%s", homedir, CONF_AXMAIL_USER_FILE);
+	mailconf = strdup(pat);
+	
+	if (stat(maildir, &fst) < 0) {
+		printf("Creating directory %s...\n", maildir);
+		if (mkdir(maildir, S_IRUSR|S_IWUSR|S_IXUSR))
+			panic("tinit: Cannot create mail directory");
+	}
+}
+
+/* Read configuration */
+ 
+int read_config(void)
+{
+	FILE *fp;
+	char line[256];
+	int ret, n = 0;
+
+	if ((fp = fopen(CONF_AXMAIL_FILE, "r")) == NULL) {
+		printf("Cannot read axmail.conf\n");
+		return -1;
+	}
+	while (fgets(line, 256, fp) != NULL) {
+		n++;
+		ret = cmdparse(cfg_cmds, line);
+		if (ret == -1)
+			printf("Syntax error in config file at line %d: %s\n", n, line);
+		if (ret < 0) {
+			fclose(fp);
+			return -1;
+		}
+	}
+	fclose(fp);
+	return 0;
+}
+
diff --git a/config.h b/config.h
new file mode 100644
index 0000000..a3f039c
--- /dev/null
+++ b/config.h
@@ -0,0 +1,44 @@
+
+#include <utmp.h>
+#include "defines.h"
+
+extern char callsign[20];
+extern char username[20];
+extern char fullname[31];
+extern char forward[79];
+
+extern char *homedir;		/* User's home directory */
+extern char *fwdfile;		/* User's .forward file (~/.forward) */
+extern char *maildir;		/* User's mail directory (~/mail) */
+extern char *mailbox;		/* System mailbox (/var/spool/mail/user) */
+extern char *userbox;		/* User's mailbox (~/mbox) */
+extern char *mailconf;		/* User's own axmail configuration */
+
+extern int local;		/* Running with user privileges? */
+
+extern char *tempMail; 		/* Temporary files: ~/mail/ax?(-pid-) */
+extern char *tempRcpt;		/* Temporary files: return receipt */
+extern char *tempNewMail;	/* Temporary files: ~/mail/axnew?(-pid-) */
+extern char *tempEdit;
+extern char *tempMesg;
+
+extern char *faxgate;		/* Email of your E-Fax Gateway */
+extern char *hostname;
+extern char *def_shell;		/* Default settings for autoaccounts */
+extern char *def_homedir;
+
+extern int mail_allowed, identification, autocreate, login_allowed;
+extern int first_uid, last_uid;
+extern gid_t user_gid;
+extern char mboxname[PATHSIZE];
+extern long IdleTimeout;
+
+struct cmd {
+	char	*name;
+	int	(*function)	(int argc, char **argv);
+};
+
+extern struct cmd Mailcmds[];
+
+extern void tinit(void);
+extern int read_config(void);
diff --git a/copying b/copying
new file mode 100644
index 0000000..dc63aac
--- /dev/null
+++ b/copying
@@ -0,0 +1,340 @@
+
+		    GNU GENERAL PUBLIC LICENSE
+		       Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+                          675 Mass Ave, Cambridge, MA 02139, USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+			    Preamble
+
+  The licenses for most software are designed to take away your
+freedom to share and change it.  By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users.  This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it.  (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.)  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+  To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have.  You must make sure that they, too, receive or can get the
+source code.  And you must show them these terms so they know their
+rights.
+
+  We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+  Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software.  If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+  Finally, any free program is threatened constantly by software
+patents.  We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary.  To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+

+		    GNU GENERAL PUBLIC LICENSE
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+  0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License.  The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language.  (Hereinafter, translation is included without limitation in
+the term "modification".)  Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope.  The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+  1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+  2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+    a) You must cause the modified files to carry prominent notices
+    stating that you changed the files and the date of any change.
+
+    b) You must cause any work that you distribute or publish, that in
+    whole or in part contains or is derived from the Program or any
+    part thereof, to be licensed as a whole at no charge to all third
+    parties under the terms of this License.
+
+    c) If the modified program normally reads commands interactively
+    when run, you must cause it, when started running for such
+    interactive use in the most ordinary way, to print or display an
+    announcement including an appropriate copyright notice and a
+    notice that there is no warranty (or else, saying that you provide
+    a warranty) and that users may redistribute the program under
+    these conditions, and telling the user how to view a copy of this
+    License.  (Exception: if the Program itself is interactive but
+    does not normally print such an announcement, your work based on
+    the Program is not required to print an announcement.)
+

+These requirements apply to the modified work as a whole.  If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works.  But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+  3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+    a) Accompany it with the complete corresponding machine-readable
+    source code, which must be distributed under the terms of Sections
+    1 and 2 above on a medium customarily used for software interchange; or,
+
+    b) Accompany it with a written offer, valid for at least three
+    years, to give any third party, for a charge no more than your
+    cost of physically performing source distribution, a complete
+    machine-readable copy of the corresponding source code, to be
+    distributed under the terms of Sections 1 and 2 above on a medium
+    customarily used for software interchange; or,
+
+    c) Accompany it with the information you received as to the offer
+    to distribute corresponding source code.  (This alternative is
+    allowed only for noncommercial distribution and only if you
+    received the program in object code or executable form with such
+    an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it.  For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable.  However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+

+  4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License.  Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+  5. You are not required to accept this License, since you have not
+signed it.  However, nothing else grants you permission to modify or
+distribute the Program or its derivative works.  These actions are
+prohibited by law if you do not accept this License.  Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+  6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions.  You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+  7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all.  For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices.  Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+

+  8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded.  In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+  9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number.  If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation.  If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+  10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission.  For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this.  Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+			    NO WARRANTY
+
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+		     END OF TERMS AND CONDITIONS
+

+	Appendix: How to Apply These Terms to Your New Programs
+
+  If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+  To do so, attach the following notices to the program.  It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) 19yy  <name of author>
+
+    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., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+    Gnomovision version 69, Copyright (C) 19yy name of author
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License.  Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary.  Here is a sample; alter the names:
+
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+  <signature of Ty Coon>, 1 April 1989
+  Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs.  If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library.  If this is what you want to do, use the GNU Library General
+Public License instead of this License.
diff --git a/defines.h b/defines.h
new file mode 100644
index 0000000..5886d90
--- /dev/null
+++ b/defines.h
@@ -0,0 +1,31 @@
+
+ /*
+  *	defines.h - Compile-time configuration
+  */
+
+#define VERSION "axMail-Fax v2.5"
+#define COPYRIGHT "(c) 1996, 1998 Heikki Hannikainen (OH7LZB) <hessu at hes.iki.fi>\nMailbox save support (c) 2003 Marius Petrescu (YO2LOJ) <mpetrescu at online.ro>\nOther modifications (c) 2005, 2006, 2015 by Brian Rogers (N1URO) <n1uro at n1uro.net> "
+#define PROMPT "=> "
+
+#define CONF_AXMAIL_FILE "/usr/local/etc/ax25/axmail.conf"
+#define CONF_AXMAIL_PROF_FILE "/usr/local/etc/ax25/ax25.profile"
+#define CONF_AXMAIL_USER_FILE ".axmailrc"
+#define DATA_AXMAIL_HELP_DIR "/usr/local/var/ax25/axmail/help/"
+#define DATA_AXMAIL_MAIL_DIR "/usr/local/var/spool/mail/"
+#define LOCK_AXMAIL_FILE "/var/lock/axmail"
+#define BIN_AXMAIL_SENDMAIL "/usr/sbin/sendmail"
+
+
+#define FORWARDFILE ".forward"
+#define USERPROFILE ".profile"
+#define PASSWDFILE "/etc/passwd"
+
+#define WELCOME "/usr/local/etc/ax25/welcome.txt"
+
+#define PATHSIZE 1024
+#define LINESIZE 1024	/* Maximum length of a line in a message */
+
+#define TRUE 1
+#define FALSE 0
+
+#define LICENSE "\n   This program is free software; you can redistribute it and/or modify\n  it under the terms of the GNU General Public License as published by\n  the Free Software Foundation; either version 2 of the License, or\n  (at your option) any later version. Usage may vary based on location.\n\n"
diff --git a/etc/axmail.conf b/etc/axmail.conf
new file mode 100644
index 0000000..72254bc
--- /dev/null
+++ b/etc/axmail.conf
@@ -0,0 +1,53 @@
+# /etc/ax25/axmail.conf - axMail configuration file
+#
+
+# Idle timeout (seconds).
+IdleTimeout	900
+
+# Local hostname.
+HostName	<your>.ampr.org
+
+# Who (of those who are listed in /etc/passwd) are allowed to use axmail
+#   all     : All users who have an account (or have just created one)
+#   nologin : Those who have "+" as password (the axmail-only accounts)
+#   passwd  : Those who have a password set (NOT those with "+" as password)
+#   axhome  : Those who put all ham home dirs within one branch
+AllowMail	all
+
+# Do we ask for a password or rely on the callsign
+#   none    : Trust the callsign given on command line
+#   passwd  : Ask for a plaintext password (brrrr...)
+# TODO: MDn authenthication !
+Identification	none
+
+#
+# ------ Parameters for automatically created user accounts
+#
+
+# Allow automatic creation of user accounts
+AutoCreate	yes
+
+# Automatically created login accounts can login (through telnet, etc)
+#   yes   : User is prompted for password, when the account is created
+#   no    : Password is set to "+" (cannot login) (preferred, axmail-only
+#           account)
+#   crazy : Password is left empty (can login without password)
+LoginAllowed	no
+
+# Group name or id for autoaccount
+AutoGroup	ax25
+
+# First user id to use for automatically created accounts
+First_uid	2000
+
+# Maximum user id
+Last_uid	2999
+
+# Where to add the home directories for the new users
+HomeDir		/home
+
+# User shell
+Shell		/bin/false
+
+# Fax Gateway - must be defined without quotes
+FaxGate		"your at faxgate.com"
diff --git a/etc/help/autofwd.hlp b/etc/help/autofwd.hlp
new file mode 100644
index 0000000..d2c9438
--- /dev/null
+++ b/etc/help/autofwd.hlp
@@ -0,0 +1,11 @@
+USAGE
+        Autofwd
+
+DESCRIPTION
+	This command will set the system to auto-forward any incoming
+	mail to this address to a "home" axMail-FAX system you would
+	usually use, OR you could set it to forward any mails from
+	this system to any SMTP based system ie: xNOS, internet, etc.
+	Just hitting the enter key will clear your mail forwarding
+	and your incoming mail to this system will be held here for you.
+
diff --git a/etc/help/delete.hlp b/etc/help/delete.hlp
new file mode 100644
index 0000000..94d9bcf
--- /dev/null
+++ b/etc/help/delete.hlp
@@ -0,0 +1,10 @@
+USAGE
+        kill [<message_number>]
+        delete [<message_number>]
+        
+DESCRIPTION
+        This command removes specified message from mailbox.
+        If no message number is entered, then command removes
+        last viewed message.
+        
+
diff --git a/etc/help/help.hlp b/etc/help/help.hlp
new file mode 100644
index 0000000..603d46b
--- /dev/null
+++ b/etc/help/help.hlp
@@ -0,0 +1,7 @@
+USAGE
+        help [<command>]
+
+DESCRIPTION
+        Gives help for the specified command or this text if no
+        command is specified. Commands can not be abbreviated.
+        Use the "?" command to retrieve a list of available commands.
diff --git a/etc/help/info.hlp b/etc/help/info.hlp
new file mode 100644
index 0000000..9f45a93
--- /dev/null
+++ b/etc/help/info.hlp
@@ -0,0 +1,2 @@
+This is an SMTP mail agent node plug-in for packet radio systems
+using linuxnode or URONode.
diff --git a/etc/help/kill.hlp b/etc/help/kill.hlp
new file mode 100644
index 0000000..94d9bcf
--- /dev/null
+++ b/etc/help/kill.hlp
@@ -0,0 +1,10 @@
+USAGE
+        kill [<message_number>]
+        delete [<message_number>]
+        
+DESCRIPTION
+        This command removes specified message from mailbox.
+        If no message number is entered, then command removes
+        last viewed message.
+        
+
diff --git a/etc/help/send.hlp b/etc/help/send.hlp
new file mode 100644
index 0000000..d2378fb
--- /dev/null
+++ b/etc/help/send.hlp
@@ -0,0 +1,7 @@
+USAGE
+        send [<mail recipient>]
+
+DESCRIPTION
+        This command sends message. If no mail recipient is specified,
+        then you will be asked.
+
diff --git a/etc/help/sfax.hlp b/etc/help/sfax.hlp
new file mode 100644
index 0000000..64b0eb1
--- /dev/null
+++ b/etc/help/sfax.hlp
@@ -0,0 +1,20 @@
+USAGE
+        sfax
+
+DESCRIPTION
+        This command sends a facsimile. The To: field will be preset for
+	you. You can specify a user but you *must* specify a full phone
+	number to fax to. Ex: n1uro at 14132416644
+
+	Notes: Faxes will send only! You will get a confirmation that your
+	fax was received into the system and another message after the
+	fax was either sent successfully or had issues sending. Faxes
+	will only work within the United States. Sending of faxes
+	elsewhere is a violation of this program.
+
+	IMPORTANT: you *must* include the beginning country code. For
+	the U.S it's 1, for the U.K. it's 011. An example of a properly
+	entered number would be: 12125551212
+
+
+
diff --git a/etc/welcome.txt b/etc/welcome.txt
new file mode 100644
index 0000000..3171913
--- /dev/null
+++ b/etc/welcome.txt
@@ -0,0 +1,11 @@
+Subject: Welcome to axMail v2.5
+
+Welcome to axmail! Your email address
+is listed above the prompt. For further
+assistance, try "?" or email root.
+
+axMail is the first mail client for packet
+that allows it's users the ability to send/receive
+receipts for their mail using just a dumb terminal.
+
+73!
diff --git a/head.c b/head.c
new file mode 100644
index 0000000..88dc58d
--- /dev/null
+++ b/head.c
@@ -0,0 +1,214 @@
+
+/* head.c - parse mail headers.
+   Grabbed from mailx 5.3b, reformatted, hacked and cleaned
+   to compile without warnings by Heikki Hannikainen <hessu at pspt.fi> */
+
+/*
+ * Copyright (c) 1980 Regents of the University of California.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms are permitted
+ * provided that this notice is preserved and that due credit is given
+ * to the University of California at Berkeley. The name of the University
+ * may not be used to endorse or promote products derived from this
+ * software without specific prior written permission. This software
+ * is provided ``as is'' without express or implied warranty.
+ */
+
+/*
+ * Mail -- a mail program
+ *
+ * Routines for processing and detecting headlines.
+ */
+
+#include <stdio.h>
+#include <ctype.h>
+
+#include "head.h"
+#include "defines.h"
+
+/*
+ * See if the passed line buffer is a mail header.
+ * Return true if yes.  Note the extreme pains to
+ * accomodate all funny formats.
+ */
+
+int ishead(char linebuf[])
+{
+	char *cp;
+	struct headline hl;
+	char parbuf[LINESIZE];
+
+	cp = linebuf;
+	if (*cp++ != 'F' || *cp++ != 'r' || *cp++ != 'o' || *cp++ != 'm' ||
+	    *cp++ != ' ')
+		return 0;
+	parse(linebuf, &hl, parbuf);
+	if (hl.l_from == NULL || hl.l_date == NULL) {
+		/* No from or date field */
+		return 0;
+	}
+	if (!isdate(hl.l_date)) {
+		/* Date field not legal date */
+		return 0;
+	}
+	/*
+	 * I guess we got it!
+	 */
+	return 1;
+}
+
+/*
+ * Split a headline into its useful components.
+ * Copy the line into dynamic string space, then set
+ * pointers into the copied line in the passed headline
+ * structure.  Actually, it scans.
+ */
+
+void parse(char line[], struct headline *hl, char pbuf[])
+{
+	char *cp, *sp;
+	char word[LINESIZE];
+
+	hl->l_from = NULL;
+	hl->l_tty = NULL;
+	hl->l_date = NULL;
+	cp = line;
+	sp = pbuf;
+	/*
+	 * Skip over "From" first.
+	 */
+	cp = nextword(cp, word);
+	cp = nextword(cp, word);
+	if (*word)
+		hl->l_from = copyin(word, &sp);
+	if (cp != NULL && cp[0] == 't' && cp[1] == 't' && cp[2] == 'y') {
+		cp = nextword(cp, word);
+		hl->l_tty = copyin(word, &sp);
+	}
+	if (cp != NULL)
+		hl->l_date = copyin(cp, &sp);
+}
+
+/*
+ * Copy the string on the left into the string on the right
+ * and bump the right (reference) string pointer by the length.
+ * Thus, dynamically allocate space in the right string, copying
+ * the left string into it.
+ */
+
+char *copyin(char *src, char **space)
+{
+	char *cp, *top;
+
+	top = cp = *space;
+	while ((*cp++ = *src++))
+		;
+	*space = cp;
+	return top;
+}
+
+#define	L	1		/* A lower case char */
+#define	S	2		/* A space */
+#define	D	3		/* A digit */
+#define	O	4		/* An optional digit or space */
+#define	C	5		/* A colon */
+#define	N	6		/* A new line */
+#define U	7		/* An upper case char */
+
+char ctypes[] = { U,L,L,S,U,L,L,S,O,D,S,D,D,C,D,D,C,D,D,S,D,D,D,D,0 };
+char tmztypes[] = { U,L,L,S,U,L,L,S,O,D,S,D,D,C,D,D,C,D,D,S,U,U,U,S,D,D,D,D,0 };
+
+/*
+ * Match the given string (cp) against the given template (tp).
+ * Return 1 if they match, 0 if they don't
+ */
+
+int cmatch(char *cp, char *tp)
+{
+
+	while (*cp && *tp)
+		switch (*tp++) {
+		case L:
+			if (!islower(*cp++))
+				return 0;
+			break;
+		case U:
+			if (!isupper(*cp++))
+				return 0;
+			break;
+		case S:
+			if (*cp++ != ' ')
+				return 0;
+			break;
+		case D:
+			if (!isdigit(*cp++))
+				return 0;
+			break;
+		case O:
+			if (*cp != ' ' && !isdigit(*cp))
+				return 0;
+			cp++;
+			break;
+		case C:
+			if (*cp++ != ':')
+				return 0;
+			break;
+		case N:
+			if (*cp++ != '\n')
+				return 0;
+			break;
+		}
+	if (*cp || *tp)
+		return 0;
+	return 1;
+}
+
+/*
+ * Test to see if the passed string is a ctime(3) generated
+ * date string as documented in the manual.  The template
+ * below is used as the criterion of correctness.
+ * Also, we check for a possible trailing time zone using
+ * the auxtype template.
+ */
+
+int isdate(char date[])
+{
+
+	if (cmatch(date, ctypes))
+		return 1;
+	return cmatch(date, tmztypes);
+}
+
+/*
+ * Collect a liberal (space, tab delimited) word into the word buffer
+ * passed.  Also, return a pointer to the next word following that,
+ * or NULL if none follow.
+ */
+
+char *nextword(char *wp, char *wbuf)
+{
+	char c;
+
+	if (wp == NULL) {
+		*wbuf = 0;
+		return NULL;
+	}
+	while ((c = *wp++) && c != ' ' && c != '\t') {
+		*wbuf++ = c;
+		if (c == '"') {
+ 			while ((c = *wp++) && c != '"')
+ 				*wbuf++ = c;
+ 			if (c == '"')
+ 				*wbuf++ = c;
+			else
+				wp--;
+ 		}
+	}
+	*wbuf = '\0';
+	for (; c == ' ' || c == '\t'; c = *wp++)
+		;
+	if (c == 0)
+		return NULL;
+	return (wp - 1);
+}
diff --git a/head.h b/head.h
new file mode 100644
index 0000000..c7e9370
--- /dev/null
+++ b/head.h
@@ -0,0 +1,19 @@
+
+/*
+ * Structure used to return a break down of a head
+ * line (hats off to Bill Joy!)
+ */
+   
+struct headline {
+	char	*l_from;	/* The name of the sender */
+	char	*l_tty;		/* His tty string (if any) */
+	char	*l_date;	/* The entire date string */
+};
+                           
+/* in head.c */
+extern char *nextword(char *wp, char *wbuf);
+extern char *copyin(char *src, char **space);
+extern void parse(char line[], struct headline *hl, char pbuf[]);
+extern int ishead(char linebuf[]);
+extern int isdate(char date[]);
+
diff --git a/lock.c b/lock.c
new file mode 100644
index 0000000..d03b056
--- /dev/null
+++ b/lock.c
@@ -0,0 +1,36 @@
+
+/* lock.c - file locking services */
+
+#include <stdio.h>
+#include <unistd.h>
+#include <string.h>
+#include <stdarg.h>
+#include <sys/file.h>
+
+#include "lock.h"
+#include "utils.h"
+
+/* Lock a file descriptor. */
+
+int lock_fd(int fd)
+{
+	if (flock(fd, LOCK_EX)) {
+		syserr("Can't lock fd\n");
+		return -1;
+	}
+
+	return 0;
+}
+
+/* Unlock a file descriptor. */
+
+int unlock_fd(int fd)
+{
+	if (flock(fd, LOCK_UN)) {
+		syserr("Can't unlockfd\n");
+		return -1;
+	}
+
+	return 0;
+}
+
diff --git a/lock.h b/lock.h
new file mode 100644
index 0000000..e5d71df
--- /dev/null
+++ b/lock.h
@@ -0,0 +1,3 @@
+
+extern int lock_fd(int fd);
+extern int unlock_fd(int fd);
diff --git a/mailcmd.c b/mailcmd.c
new file mode 100644
index 0000000..c3474e9
--- /dev/null
+++ b/mailcmd.c
@@ -0,0 +1,526 @@
+
+/* mailcmd.c - Mail commands */
+ 
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/stat.h>
+#include <syslog.h>
+
+#include "mailcmd.h"
+#include "defines.h"
+#include "config.h"
+#include "mbox.h"
+#include "utils.h"
+
+/* List messages */
+
+void printhead(int i, struct message *m) {
+	char ch = ' ';
+	
+	if ((m->m_flag & (MREAD|MNEW)) == MNEW)
+		ch = 'N';
+	if ((m->m_flag & (MREAD|MNEW)) == 0)
+		ch = 'U';
+	if ((m->m_flag & (MDELETED)) == MDELETED)
+		ch = 'K';
+		
+	printf("%c%c%4i %25.25s%6li %.39s\n",
+		(current == i+1) ? '>' : ' ',
+		ch, i+1, m->from, m->m_size, m->subj);
+}
+
+int do_list(int argc, char **argv)
+{
+	int i;
+	
+	if (!(messages)) {
+		printf("No messages.\n");
+		return 0;
+	}
+	
+	printf("   Num From                       Size Subject\n");
+	
+	for (i = 0; i < messages; i++) {
+		printhead(i, &message[i]);
+	}
+
+	return 0;
+}
+
+/* Read a message (xNOS-stylish parameters) */
+
+int do_read(int argc, char **argv)
+{
+	char *myargv[64];
+	int myargc, argsmine;
+	char *tmpbuf;
+	int i;
+	int msg, maxmsg;
+
+	if (!(messages)) {
+		printf("You have no messages.\n");
+		return 0;
+	}
+
+	if (argc > 1) {
+		argsmine = 0;
+		for (i = 1; i < argc; i++)
+			myargv[i] = argv[i];
+		myargc = argc;
+	} else {
+		argsmine = 1;
+		if (current >= messages) {
+			printf("No more messages.\n");
+			return 0;
+		}
+		current++;
+		myargc = 2;
+		myargv[1] = malloc(17);
+		sprintf(myargv[1], "echo");
+		sprintf(myargv[1], "%i", current);
+	}
+
+	for (i = 1; i < myargc; i++) {
+		tmpbuf = strchr(myargv[i], '-');
+		msg = atoi(myargv[i]);
+		if (tmpbuf == NULL)
+			maxmsg = msg;
+		else
+			maxmsg = atoi(++tmpbuf);
+		if (maxmsg < msg) {
+			printf("Bad message number %i.\n", maxmsg);
+			continue;
+		}
+		for (; msg <= maxmsg; msg++) {
+			if (msg < 1 || msg > messages) {
+				printf("There's no message number %i.\n", msg);
+				continue;
+			}
+			readmesg(msg, (!strncmp(argv[0], "v", 1)));
+			printf("\n");
+			if (dot->receipt != NULL) {
+			printf("\aA receipt was asked for. Use the SR command to make one.\n");
+			}
+		}
+	}
+	
+	if (argsmine)
+		for (i = 1; i < myargc; i++)
+			free(myargv[i]);
+
+	return 0;
+	                          if (dot->receipt != NULL) {
+                                printf("Receipt is needed\n");
+                                return 0;
+			}
+
+}
+
+/* Send a message (perhaps a reply) */
+ 
+int do_send(int argc, char **argv)
+{
+	FILE *f;
+	FILE *g;
+	char str[LINESIZE + 1];
+	int i;
+
+	int reply = 0;
+
+	if (!strncmp(argv[0], "sr", 2)) {
+		reply = 1;
+		if (argc == 1) {
+			if (current == 0) {
+				printf("No current message to reply to.\n");
+				return 0;
+			}
+			i = current;
+		} else
+			i = atoi(argv[1]);
+
+		i--;
+		if ((i < 0) || (i >= messages)) {
+			printf("There's no message %s.\n", argv[1]);
+			return 0;
+		}
+
+		dot = &message[i];
+	}
+	
+	if ((f = fopen(tempMesg, "w")) == NULL) {
+		printf("Could not create temporary file.\n");
+		syslog(LOG_NOTICE, "do_send: Could not create temporary file.\n");
+		return 0;
+	}
+
+	fprintf(f, "From: %s <%s@%s>\n", fullname, username, hostname);
+       
+	str[0] = '\0';
+	if (argc != 1)	/* Recipient on command line */
+		for (i = 1; i < argc; i++) {
+			if (i > 1)
+				strcat(str, " ");
+			strncat(str, argv[i], LINESIZE - strlen(str));
+		}
+	else {
+		if (reply) {
+			strncpy(str, dot->from, LINESIZE);
+			printf("To: %s\n", str);
+		} else {
+			getstr(str, LINESIZE, "To: ");
+			if (str[0] == '\0') {
+				printf("No recipients, message cancelled.\n");
+				fclose(f);
+				remove(tempMesg);
+				return 0;
+			}
+		}
+	}
+	
+	fprintf( f, "To: %s\n", str);
+	fprintf( f, "X-Mailer: %s\n", VERSION );
+	fprintf( f, "X-Origin: Amateur Radio Services\n" );
+	goto prio;;
+	
+	/* adding priority receive rule */
+
+prio:
+	getstr(str, LINESIZE, "Is this message emergency or urgent? (y/N/?): ");
+	
+	/* try to bullet-proof end-user responces a bit... */
+		
+	if (!strcmp(str, "?")) {
+		printf("\nAnswering \"Y\" or \"yes\" here will flag the message as of being highest\n");
+		printf("priority in nature and with most mail client software will present\n");
+		printf("your message as an urgent read communication. By entering \"N\" or \"no\" or\n");
+		printf("by hitting the enter key will send your mail message via normal delivery.\n\n");
+		goto prio;
+	}
+				
+	if (!strcasecmp(str, "Y") || !strcasecmp (str, "YES") || !strcasecmp (str, "YE")) {
+		fprintf( f, "X-Priority: 1 (Highest)\n" );
+		}
+		else
+		{ fprintf( f,"X-Priority: 3 (Normal)\n" );
+		}
+
+receipt:
+	getstr(str, LINESIZE, "Read receipt requested? (y/N/?): ");
+
+        if (!strcmp(str, "?")) {
+                printf("\nAnswering \"Y\" or \"yes\" here will request a confirmation of \n");
+                printf("your message being opened by the remote user. By entering \"N\" or \"no\" or\n");
+                printf("by hitting the enter key will not request a confirmation receipt.\n\n");
+                goto receipt;
+        }
+
+        if (!strcasecmp(str, "Y") || !strcasecmp (str, "YES") || !strcasecmp (str, "YE")) {
+                fprintf( f, "Disposition-Notification-To: %s <%s@%s>\n", fullname, username, hostname);
+                }
+                else
+                { fprintf( f,"" );
+                }
+		
+	if (reply) {
+		if (strncasecmp(dot->subj, "Re: ", 3))
+			snprintf(str, LINESIZE, "Re: %s", dot->subj);
+		else
+			snprintf(str, LINESIZE, "%s", dot->subj);
+		printf("Subject: %s\n", str);
+	} else
+		getstr(str, LINESIZE, "Subject: ");
+		
+	fprintf(f, "Subject: %s\n", str);
+	
+	if (reply)
+		fprintf(f, "In-Reply-To: %s\n", dot->id);
+	
+	printf("Enter message text (end with \"/ex\" or \".\" on a line by itself):\n");
+	fflush(stdout);
+
+cont:
+	do {
+		fgets(str, LINESIZE, stdin);
+		if ( strcmp( str, ".\n") && strcmp( str, "/ex\n")) fputs(str, f);
+	} while (strcmp(str, ".\n") && strcmp(str, "/ex\n"));
+
+retry:
+	getstr(str, LINESIZE, "Deliver (Y/n/c/?): ");
+	if (!strcmp(str, "?")) {
+		printf("Answering \"N\" here will cancel the message. Answering \"C\" will\n");
+		printf("let you continue writing the message. Answering anything else will\n");
+		printf("proceed with delivering the message to the recipient.\n");
+		goto retry;
+	}
+	if (!strcasecmp(str, "c")) {
+		printf("Continue entering message text\n(end with \"/ex\" or \".\" on a line by itself):\n");
+		fflush(stdout);
+		goto cont;
+	}
+	
+	if (fclose(f)) {
+		printf("Ouch, could not close temporary file.\n");
+		syslog(LOG_NOTICE, "do_send: Could not close temporary file.\n");
+		return 0;
+	}
+	
+	if (strcasecmp(str, "n")) {
+		getstr(str, LINESIZE, "Request a delivery receipt? (y/N): ");
+			if (!strcasecmp(str, "y")) {
+			sprintf(str, "%s -N success,delay,failure -oem -t < %s", BIN_AXMAIL_SENDMAIL, tempMesg);
+			system(str);
+			printf("Message sent, delivery notification activated.\n");
+		} else {
+			sprintf(str, "%s -oem -t < %s", BIN_AXMAIL_SENDMAIL, tempMesg);
+			system(str);
+			printf("Message sent.\n");
+		}
+	} else
+		printf("Message canceled.\n");
+	
+	if (remove(tempMesg)) {
+		printf("Ouch, could not remove temporary file.\n");
+		syslog(LOG_NOTICE, "do_send: Could not remove temporary file.\n");
+		return 0;
+	}
+
+	return 0;
+}
+
+/* Kill a message */
+ 
+int do_kill(int argc, char **argv)
+{
+	int i, msg = 0, cnt = 0;
+	char *myargv[64];
+	int myargc, argsmine;
+
+	if (!(messages)) {
+		printf("You have no messages.\n");
+		return 0;
+	}
+
+	if (argc > 1) {
+		argsmine = 0;
+		for (i = 1; i < argc; i++)
+			myargv[i] = argv[i];
+		myargc = argc;
+	} else {
+		if (current == 0) {
+			printf("No current message to kill.\n");
+			return 0;
+		}
+		argsmine = 1;
+		myargc = 2;
+		myargv[1] = malloc(17);
+		sprintf(myargv[1], "%i", current);
+	}
+
+	for (i = 1; i < myargc; i++) {
+		msg = atoi(myargv[i]) - 1;
+
+		if ((msg < 0) || (msg >= messages)) {
+			printf("There's no message %s.\n", myargv[i]);
+			continue;
+		}
+
+		dot = &message[msg];
+
+		if ((dot->m_flag & MDELETED) == MDELETED) {
+			printf("Message %i is already dead.\n", msg + 1);
+			continue;
+		}
+		
+		dot->m_flag |= MDELETED;
+		cnt++;
+	}
+	
+	if (cnt == 1) /* GCC warns here, but what the heck! 8-) */
+		printf("Message %i killed.\n", msg + 1);
+	else if (cnt > 1)
+		printf("%i messages killed.\n", cnt);
+
+	if (argsmine)
+		for (i = 1; i < myargc; i++)
+			free(myargv[i]);
+
+	return 0;
+}
+
+/* Unkill a message */
+ 
+int do_unkill(int argc, char **argv)
+{
+	int i, msg = 0, cnt = 0;
+	char *myargv[64];
+	int myargc, argsmine;
+
+	if (!(messages)) {
+		printf("You have no messages.\n");
+		return 0;
+	}
+
+	if (argc > 1) {
+		argsmine = 0;
+		for (i = 1; i < argc; i++)
+			myargv[i] = argv[i];
+		myargc = argc;
+	} else {
+		if (current == 0) {
+			printf("No current message to unkill.\n");
+			return 0;
+		}
+		argsmine = 1;
+		myargc = 2;
+		myargv[1] = malloc(17);
+		sprintf(myargv[1], "%i", current);
+	}
+
+	for (i = 1; i < myargc; i++) {
+		msg = atoi(myargv[i]) - 1;
+
+		if ((msg < 0) || (msg >= messages)) {
+			printf("There's no message %s.\n", myargv[i]);
+			continue;
+		}
+
+		dot = &message[msg];
+
+		if ((dot->m_flag & MDELETED) != MDELETED) {
+			printf("Message %i is not dead.\n", msg + 1);
+			continue;
+		}
+		
+		dot->m_flag ^= (dot->m_flag & MDELETED);
+		cnt++;
+	}
+	
+	if (cnt == 1) /* GCC warns here, but what the heck! 8-) */
+		printf("Message %i unkilled.\n", msg + 1);
+	else if (cnt > 1)
+		printf("%i messages unkilled.\n", cnt);
+
+	if (argsmine)
+		for (i = 1; i < myargc; i++)
+			free(myargv[i]);
+
+	return 0;
+}
+
+/* Send a Fax */ 
+int do_fax(int argc, char **argv)
+{
+        FILE *f;
+	char str[LINESIZE + 1];
+	int i;
+
+        int reply = 0;
+
+        if (!strncmp(argv[0], "sr", 2)) {
+                reply = 1;
+                if (argc == 1) {
+                        if (current == 0) {
+                                printf("No current message to reply to.\n");
+                                return 0;
+                        }
+                        i = current;
+                } else
+                        i = atoi(argv[1]);
+
+                i--;
+                if ((i < 0) || (i >= messages)) {
+                        printf("There's no message %s.\n", argv[1]);
+                        return 0;
+                }
+
+                dot = &message[i];
+        }
+
+        if ((f = fopen(tempMesg, "w")) == NULL) {
+                printf("Could not create temporary file.\n");
+                syslog(LOG_NOTICE, "do_send: Could not create temporary file.\n");
+                return 0;
+        }
+
+        fprintf(f, "From: %s <%s@%s>\n", fullname, username, hostname);
+
+        str[0] = '\0';
+        if (argc != 1)  /* Recipient on command line */
+                for (i = 1; i < argc; i++) {
+                        if (i > 1)
+                                strcat(str, " ");
+                        strncat(str, argv[i], LINESIZE - strlen(str));
+                }
+        else {
+        }
+
+	printf("To: Fax Gateway\n");
+	fprintf( f, "To: %s\n", faxgate );
+        fprintf( f, "X-Mailer: %s\n", VERSION );
+        fprintf( f, "X-Origin: Amateur Radio Services\n" );
+        goto prio;;
+
+        /* adding priority receive rule */
+
+prio:
+/*         if (reply) {
+                if (strncasecmp(dot->subj, "Re: ", 3))
+                        snprintf(str, LINESIZE, "Re: %s", dot->subj);
+                else
+                        snprintf(str, LINESIZE, "%s", dot->subj);
+                printf("Subject: %s\n", str);
+        } else */
+		getstr(str, LINESIZE, "Enter a header <firstname at fullphone Brief note here>\nEx: john at 16195551212 Hi From Packet\nHeader: ");
+
+	fprintf(f, "Subject: %s\n", str);
+
+        if (reply)
+                fprintf(f, "In-Reply-To: %s\n", dot->id);
+
+        printf("Enter fax message (end with \"/ex\" or \".\" on a line by itself):\n");
+        fflush(stdout);
+
+cont:
+        do {
+/*                fprintf( f, "X-Mailer: %s\n", VERSION );
+		fprintf( f, "X-Origin: Amateur Radio Services\n" ); */
+		fgets(str, LINESIZE, stdin);
+                if ( strcmp( str, ".\n") && strcmp( str, "/ex\n")) fputs(str, f);
+        } while (strcmp(str, ".\n") && strcmp(str, "/ex\n"));
+
+retry:
+        getstr(str, LINESIZE, "Deliver (Y/n/c/?): ");
+        if (!strcmp(str, "?")) {
+                printf("Answering \"N\" here will cancel the message. Answering \"C\" will\n");
+                printf("let you continue writing the message. Answering anything else will\n");
+                printf("proceed with delivering the message to the recipient.\n");
+                goto retry;
+        }
+        if (!strcasecmp(str, "c")) {
+                printf("Continue entering message text\n(end with \"/ex\" or \".\" on a line by itself):\n");
+                fflush(stdout);
+                goto cont;
+        }
+
+        if (fclose(f)) {
+                printf("Ouch, could not close temporary file.\n");
+                syslog(LOG_NOTICE, "do_send: Could not close temporary file.\n");
+                return 0;
+        }
+
+        if (strcasecmp(str, "n")) {
+                sprintf(str, "%s -oem -t < %s", BIN_AXMAIL_SENDMAIL, tempMesg);
+                system(str);
+                printf("Message sent.\n");
+        } else
+                printf("Message canceled.\n");
+
+        if (remove(tempMesg)) {
+                printf("Ouch, could not remove temporary file.\n");
+                syslog(LOG_NOTICE, "do_send: Could not remove temporary file.\n");
+                return 0;
+        }
+
+        return 0;
+}
diff --git a/mailcmd.h b/mailcmd.h
new file mode 100644
index 0000000..9938a8c
--- /dev/null
+++ b/mailcmd.h
@@ -0,0 +1,9 @@
+
+/* in mailcmd.c */
+extern int do_list(int argc, char **argv);
+extern int do_read(int argc, char **argv);
+extern int do_send(int argc, char **argv);
+extern int do_fax(int argc, char **argv);
+extern int do_kill(int argc, char **argv);
+extern int do_unkill(int argc, char **argv);
+
diff --git a/mbox.c b/mbox.c
new file mode 100644
index 0000000..b1df805
--- /dev/null
+++ b/mbox.c
@@ -0,0 +1,357 @@
+
+/*
+ *	mbox.c - Read, parse and write the system mailbox
+ *
+ *	Much taken from mailx-5.3b, which is 
+ *	Copyright (c) 1980 Regents of the University of California.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <ctype.h>
+#include <fcntl.h>
+#include <syslog.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <string.h>
+
+#include "mbox.h"
+#include "utils.h"
+#include "defines.h"
+#include "config.h"
+#include "head.h"
+
+FILE *mbox;			/* Temporary mailbox in /tmp */
+struct message *message;	/* Message list */
+struct message *dot;		/* Current message pointer */
+int messages = 0;		/* Amount of messages in list */
+int current = 0;		/* Current message index */
+int newm = 0;			/* New messages */
+
+long sysboxlen = 0;		/* Length of the system mailbox at reading */
+				/* It will increase if new arrives */
+
+/* Check if we have this message in the message list yet */
+
+int havemessage(char *id)
+{
+	int i;
+	
+	for (i = 0; i < messages; i++) {
+		if (!strcmp(message[i].id, id))
+			return 1;
+	}
+	
+	return 0;
+}
+
+/* Open a temp file by creating and unlinking.
+   Return the open file descriptor. */
+
+int opentemp(char file[])
+{
+	int f;
+	
+	if ((f = open(file, O_CREAT|O_EXCL|O_RDWR, 0600)) < 0)
+		panic("opentemp: could not open file");
+	remove(file);
+	return f;
+}
+
+/* Take the data out of the passed ghost file and toss it into
+   a dynamically allocated message structure. */
+
+void makemessage(FILE *f)
+{
+	int size = (messages + 1) * sizeof (struct message);
+
+	if (message != 0)
+		free((char *) message);
+	if ((message = (struct message *) malloc((unsigned) size)) == 0)
+		panic("Insufficient memory for %d messages", messages);
+	dot = message;
+	size -= sizeof (struct message);
+	fflush(f);
+	lseek(fileno(f), (long) sizeof *message, 0);
+	if (read(fileno(f), (char *) message, size) != size)
+		panic("Message temporary file corrupted");
+	message[messages].m_size = 0;
+	message[messages].m_lines = 0;
+	message[messages].receipt = NULL;
+	message[messages].from = NULL;
+	message[messages].date = NULL;
+	message[messages].subj = NULL;
+	message[messages].id = NULL;
+	fclose(f);
+}
+
+/* Append the passed message descriptor onto the temp file.
+   If the write fails, return 1, else 0 */
+
+void append(struct message *mp, FILE *f)
+{
+	if (fwrite((char *) mp, sizeof *mp, 1, f) != 1)
+		panic("append: Could not append message");
+}
+
+/* Copy mailbox from ~/mail/mbox and /var/spool/mail to /tmp
+   (yo2loj - 13 april 2003) */
+
+int getmail(void)
+{
+	struct stat stb;
+
+	FILE *ibuf;
+	FILE *mestmp;
+
+	char buf[LINESIZE];
+	int count;
+
+	long offset = 0;
+	int inheader = 0;
+	int maybe = 1;
+	char *cp = NULL;
+	char c;
+
+
+	struct message this = { MUSED|MNEW, 0, 0, 0 };
+	
+	
+	if ((mbox = fopen(tempMail, "w")) == NULL)
+		panic("getmail: Could not create temporary file");
+
+	
+	if ((ibuf = fopen(userbox, "r")) == NULL) goto sysbox;
+	
+	if (fstat(fileno(ibuf), &stb) < 0) {
+		printf("Ouch, could not fstat() mailbox.\n");
+		syslog(LOG_NOTICE, "getmail: Could not fstat()");
+		fclose(ibuf);
+		goto sysbox;;
+	}
+	
+	switch (stb.st_mode & S_IFMT) {
+		case S_IFREG:		/* Good, a regular file */
+			break;
+		default:		/* Yuck, i won't eat THAT! */
+			fclose(ibuf);
+			goto sysbox;
+	}
+	
+	if (stb.st_size == 0) {		/* Zero-sized mailbox? */
+		fclose(ibuf);
+		goto sysbox;;
+	}
+	
+	/* copy old read mail */
+	
+	while (fgets(buf, LINESIZE, ibuf) != NULL) {
+	    count = strlen(buf);
+	    fwrite(buf, sizeof *buf, count, mbox);
+	    if (ferror(mbox))
+			panic("getmail: Could not write temporary file");	
+	}
+
+	fclose(ibuf);
+	
+sysbox:
+	if ((ibuf = fopen(mailbox, "r")) == NULL) goto rdexit;
+	
+	if (fstat(fileno(ibuf), &stb) < 0) {
+		printf("Ouch, could not fstat() mailbox.\n");
+		syslog(LOG_NOTICE, "getmail: Could not fstat()");
+		fclose(ibuf);
+		goto rdexit;
+	}
+	
+	switch (stb.st_mode & S_IFMT) {
+		case S_IFREG:		/* Good, a regular file */
+			break;
+		default:		/* Yuck, i won't eat THAT! */
+			fclose(ibuf);
+			goto rdexit;
+	}
+	
+	if (stb.st_size == 0) {		/* Zero-sized mailbox? */
+		fclose(ibuf);
+		goto rdexit;
+	}
+	
+	/* copy unread and new mail */
+	
+	while (fgets(buf, LINESIZE, ibuf) != NULL) {
+	    count = strlen(buf);
+	    fwrite(buf, sizeof *buf, count, mbox);
+	    sysboxlen += count;
+	    if (ferror(mbox))
+			panic("getmail: Could not write temporary file");
+	}
+	
+	fclose(ibuf);
+
+rdexit:
+	fclose(mbox);	/* all mail is now in temp file - digest it! */
+
+	if ((c = opentemp(tempMesg)) < 0)
+		exit(1);
+		
+	if ((mestmp = fdopen(c, "r+")) == NULL)
+		panic("getmail: Could not open temporary file");
+
+	if ((mbox = fopen(tempMail, "r")) == NULL)
+		panic("getmail: Could not open temporary file");
+
+
+	for (;;) {
+		if (fgets(buf, LINESIZE, mbox) == NULL) {
+		    /* End of file */
+		    append(&this, mestmp);
+		    makemessage(mestmp);
+		    if (fclose(mbox))
+		    	panic("getmail: Could not close temporary mailbox");
+		    return 0;
+		}
+		count = strlen(buf);
+		buf[count - 1] = '\0';
+		if (maybe && buf[0] == 'F' && ishead(buf)) {
+			messages++;
+			newm++;
+			append(&this, mestmp);
+			this.m_flag = MUSED|MNEW;
+			this.m_size = 0;
+			this.m_lines = 0;
+			this.m_offset = offset;
+			this.subj = NULL;
+			this.from = NULL;
+			this.date = NULL;
+			this.id = NULL;
+			inheader = 1;
+		} else if (buf[0] == 0) {
+			inheader = 0;
+		} else if (inheader) {
+			if (!strncasecmp(buf, "Status: ", 8)) {
+				cp = &buf[8];
+				if (strchr(cp, 'R') != NULL)
+					this.m_flag |= MREAD;
+				if (strchr(cp, 'O') != NULL) {
+					this.m_flag &= ~MNEW;
+					newm--;
+				}
+			}
+			
+                        if ((!strncasecmp(buf, "Disposition-Notification-To:", 28)) && (this.receipt == NULL)) {
+                                cp = &buf[28];
+                                while ((*cp) && (isspace(*cp)))
+                                        cp++;
+                                this.receipt = strdup(cp);
+                        }
+
+			if ((!strncasecmp(buf, "Subject:", 8)) && (this.subj == NULL)) {
+				cp = &buf[8];
+				while ((*cp) && (isspace(*cp)))
+					cp++;
+				this.subj = strdup(cp);
+			}
+			
+			if ((!strncasecmp(buf, "From:", 5)) && (this.from == NULL)) {
+				cp = &buf[5];
+				while ((*cp) && (isspace(*cp)))
+					cp++;
+				this.from = strdup(cp);
+			}
+			
+			if ((!strncasecmp(buf, "Date:", 5)) && (this.date == NULL)) {
+				cp = &buf[5];
+				while ((*cp) && (isspace(*cp)))
+					cp++;
+				this.date = strdup(cp);
+			}
+
+			if ((!strncasecmp(buf, "Message-ID:", 11)) && (this.id == NULL)) {
+				cp = &buf[11];
+				while ((*cp) && (isspace(*cp)))
+					cp++;
+				this.id = strdup(cp);
+			}
+		}
+		offset += count;
+		this.m_size += count;
+		this.m_lines++;
+		maybe = buf[0] == 0;
+
+	}
+	
+	
+	return 0;
+}
+
+/* Read a message */
+ 
+int readmesg(int msg, int verbose)
+{
+	int i, line = 0;
+	int inhdr = 1;
+	char buf[LINESIZE];
+	
+	if ((msg < 1) || (msg > messages)) {
+		printf("There's no message %i.\n", msg);
+		return -1;
+	}
+
+	if ((mbox = fopen(tempMail, "r")) == NULL) {
+		printf("Could not open temporary mailbox.\n");
+		return -1;
+	}
+
+	i = msg - 1;
+	dot = &message[i];
+
+	if (fseek(mbox, dot->m_offset, SEEK_SET)) {
+		printf("readmesg: Could not fseek to message %i.\n", msg);
+		return -1;
+	}
+	
+	current = msg;
+	
+	printf("Message %i:%s%s%s\n", msg, 
+		((dot->m_flag & (MREAD|MNEW)) == MNEW) ? " (New)" : "",
+		((dot->m_flag & (MREAD|MNEW)) == 0) ? " (Unread)": "",
+		((dot->m_flag & (MDELETED)) == MDELETED) ? " (Deleted)" : ""
+		);
+		
+	dot->m_flag |= MREAD;
+	dot->m_flag ^= (dot->m_flag & MNEW);
+	
+	for (;;) {
+		if (fgets(buf, LINESIZE, mbox) == NULL) {
+			/* End of file */
+			fclose(mbox);
+			return 0;
+		}
+		line++;
+		if (inhdr) {
+			/* Headers */
+			if (((verbose) && (line != 1) && (strncasecmp(buf, "Status: ", 8)) && (strncasecmp(buf, "X-Status: ", 10)) ) ||
+			    (!strncasecmp(buf, "Date:", 5)) ||
+			    (!strncasecmp(buf, "From:", 5)) ||
+			    (!strncasecmp(buf, "To:", 3)) ||
+			    (!strncasecmp(buf, "Cc:", 3)) ||
+			    (!strncasecmp(buf, "Subject:", 8)))
+				printf("%s", buf);
+
+			if (!strcmp("\n", buf)) {
+				inhdr = 0;
+			}
+		} else {
+			/* Data */
+			if (line == dot->m_lines) {
+				fclose(mbox);
+				return 0;
+			}
+			printf("%s", buf);
+		}
+
+	}
+	return 0;
+
+}
diff --git a/mbox.h b/mbox.h
new file mode 100644
index 0000000..c3d916a
--- /dev/null
+++ b/mbox.h
@@ -0,0 +1,46 @@
+/*
+ * flag bits.
+ */
+
+#define MUSED		(1<<0)		/* entry is used, but this bit isn't */
+#define MDELETED	(1<<1)		/* entry has been deleted */
+#define MSAVED		(1<<2)		/* entry has been saved */
+#define MTOUCH		(1<<3)		/* entry has been noticed */
+#define MPRESERVE	(1<<4)		/* keep entry in sys mailbox */
+#define MMARK		(1<<5)		/* message is marked! */
+#define MODIFY		(1<<6)		/* message has been modified */
+#define MNEW		(1<<7)		/* message has never been seen */
+#define MREAD		(1<<8)		/* message has been read sometime. */
+#define MSTATUS		(1<<9)		/* message status has changed */
+
+/*
+ * Structure used in the message list
+ */
+
+struct message {
+	short	m_flag;			/* flags, see below */
+	long	m_offset;		/* offset of message */
+	long	m_size;			/* Bytes in the message */
+	short	m_lines;		/* Lines in the message */
+	char	*receipt;		/* Receipt request */
+	char	*notify;		/* Delivery notify */
+	char	*from;			/* From */
+	char	*date;			/* Date string */
+	char	*subj;			/* Subject line */
+	char	*id;			/* Message ID */
+	char	*whoti;			/* Who to send a fax to */
+	char	*phone;			/* Phone to fax */
+	char	*note;			/* Note for fax cover */
+};
+
+extern FILE *mbox;		/* Temporary mailbox in /tmp */
+extern struct message *message;	/* Message list */
+extern struct message *dot;	/* Current message pointer */
+extern int messages;		/* Amount of messages in list */
+extern int current;		/* Current message index */
+extern int newm;		/* New messages */
+
+extern long sysboxlen;		/* System mailbox length at start */
+
+extern int getmail(void);
+extern int readmesg(int msg, int verbose);
diff --git a/quit.c b/quit.c
new file mode 100644
index 0000000..ff46a1a
--- /dev/null
+++ b/quit.c
@@ -0,0 +1,250 @@
+
+/* quit.c - clean things up on exit. */
+ 
+#include <stdio.h>
+#include <sys/stat.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "utils.h"
+#include "quit.h"
+#include "config.h"
+#include "lock.h"
+#include "mbox.h"
+
+/* Remove a temporary file, if it exists */
+
+void cleartmp(char *fname)
+{
+	struct stat fst;
+
+	if (!stat(fname, &fst)) 
+		if (remove(fname))
+			printf("Ouch, couldn't remove %s.\n", fname);
+}
+
+/* Update system and user mailbox
+   (yo2loj - 13 april 2003) */
+ 
+int save_mbox(void)
+{
+	FILE *mb;
+	FILE *nm;
+	FILE *ub;
+	FILE *tmp;
+	FILE *dest;
+	
+	long mblen=0;
+	int havenew = 0;
+	
+	char buf[LINESIZE];
+	int count;
+		
+	int i, line;
+	int inhdr;
+	char *status;
+	int hasstatus;
+	
+	mb = fopen(mailbox, "r");
+	if (lock_fd(fileno(mb)))
+		return -1;
+
+	fseek(mb, 0, SEEK_END);
+	mblen = ftell(mb);
+	
+	if (mblen < sysboxlen) {
+	    printf("Mailbox changed by another program. Mailbox not saved.");
+	    unlock_fd(fileno(mb));
+	    fclose(mb);
+	    return -1;
+	}
+	
+	if (mblen > sysboxlen) {
+	    printf("New mail has arrived.\n");
+	    havenew = 1;
+	    
+	    /* copy new mail to a temp file, will append to system mailbox later */
+	    
+	    if ((nm =  fopen(tempNewMail, "w+")) == NULL)
+		panic("save_mbox: Could not create temporary file");
+
+	    fseek(mb, sysboxlen, SEEK_SET);
+	    
+	    while (fgets(buf, LINESIZE, mb) != NULL) {
+		count = strlen(buf);
+		fwrite(buf, sizeof *buf, count, nm);
+		if (ferror(nm))
+		    panic("save_mbox: Could not write temporary file");
+	    }
+	    
+	}
+	
+	if ((tmp = fopen(tempMail, "r")) == NULL)
+	    panic("save_mbox: Could not open temporary mail file");
+	    
+	if (freopen(mailbox, "w", mb) == NULL)
+	    panic("save_mbox: Could not open system mailbox for writing");
+	    
+	if ((ub = fopen(userbox, "w")) == NULL) {
+	    /* error on user mailbox,
+	       dump all to the system mailbox as last resort */
+	       
+	    while (fgets(buf, LINESIZE, tmp) != NULL) {
+		count = strlen(buf);
+		fwrite(buf, sizeof *buf, count, mb);
+		if (ferror(mb))
+		    panic("save_mbox: Could not write to system mailbox.");
+	    }
+	    fclose(tmp);
+	    if (havenew) {
+		fseek(nm, 0, SEEK_SET);
+		while (fgets(buf, LINESIZE, nm) != NULL) {
+		    count = strlen(buf);
+		    fwrite(buf, sizeof *buf, count, mb);
+		    if (ferror(mb))
+			panic("save_mbox: Could not write to system mailbox.");
+		}
+		fclose(nm);
+	    }
+	    unlock_fd(fileno(mb));
+	    fclose(mb);
+	    printf("Could not open user mailbox, dumping to system mailbox\n");
+	    return -1;
+	}
+	
+	/* 
+	   we have all processed messages in tmp and
+	   any newly arrived (if any) in nm.
+	   System mailbox is locked, empty and opened for write (mb),
+	   User Mailbox is empty and opened for writing (ub).
+	   
+	   	- read message go to ~/mbox with status RO
+		- not read go back to system mailbox with status O
+		- deleted are purged
+		- any arrived go to system mailbox as they are
+	*/
+	
+	for (i=0; i<messages; i++) {
+	    dot = &message[i];	
+	    if (fseek(tmp, dot->m_offset, SEEK_SET)) {
+		printf("save_mbox: Could not find message %i.\n", i);
+		continue;
+	    }
+	    
+	    if (dot->m_flag & MDELETED) {
+		dest = NULL;
+		status = NULL;
+	    }
+	    else if (dot->m_flag & MREAD) {
+		dest = mb;
+		status = "RO";
+	    }
+	    else if (dot->m_flag & MNEW) {
+		dest = mb;
+		status = "O";
+	    }
+	    else {
+		dest = mb;
+		status = NULL;
+	    }
+	    
+	    line = 0;
+	    hasstatus = 0;
+	    inhdr = 1;
+	    
+	    for (;;) {
+		if (!dest) break;
+		if (fgets(buf, LINESIZE, tmp) == NULL) {
+		    /* End of file */
+		    break;
+		}
+		line ++;
+		if (inhdr) {
+		    /* Header */
+		    if (!strncasecmp(buf, "Status: ", 8)) {
+			hasstatus = 1;
+			if (status) sprintf(buf, "Status: %s\n", status);
+		    } else if (!strcmp("\n", buf)) {
+			inhdr = 0;
+			if (!hasstatus) {
+			    if (status) sprintf(buf, "Status: %s\n", status);
+			    fwrite(buf, sizeof *buf, strlen(buf), dest);
+			}
+			strcpy(buf, "\n");
+		    }
+		} else {
+		    /* Data */
+		    if (line == dot->m_lines + 1) break;
+		}
+		fwrite(buf, sizeof *buf, strlen(buf), dest);
+	    }
+	}
+	
+	fclose(tmp);
+		
+	if (havenew) {
+	    /* append the newly arrived mail */
+	    fseek(nm, 0, SEEK_SET);
+	    freopen(mailbox, "a+", mb);
+	    while (fgets(buf, LINESIZE, nm) != NULL) {
+		count = strlen(buf);
+		fwrite(buf, sizeof *buf, count, mb);
+		if (ferror(mb))
+		    panic("save_mbox: Could not write to system mailbox.");
+	    }
+	    
+	    fclose(nm);
+	}
+	
+	unlock_fd(fileno(mb));
+	fclose(mb);
+	fclose(ub);
+
+	return 0;
+}
+
+/* On quit without save: check and announce if new mail has arrived */
+ 
+int chk_new_msg(void)
+{
+	FILE *mb;
+	long mblen=0;
+	
+	mb = fopen(mailbox, "r");
+	if (lock_fd(fileno(mb)))
+		return -1;
+
+	fseek(mb, 0, SEEK_END);
+	mblen = ftell(mb);
+	
+	if (mblen != sysboxlen) printf("New mail has arrived.\n");
+
+	unlock_fd(fileno(mb));
+	fclose(mb);
+
+	return 0;
+}
+
+/* quit. */
+
+void quit(int save, int code)
+{
+	if (save) {
+		printf("Exiting, saving changes in mailbox.\n");
+	} else
+		printf("Cancelling changes, mailbox not changed.\n");
+	if (save) {
+		save_mbox();
+	}
+	else
+		chk_new_msg();
+	printf("Bye %s! from axMail@%s.\n", username, hostname);	
+	cleartmp(tempMail);
+	cleartmp(tempNewMail);
+	cleartmp(tempEdit);
+	cleartmp(tempMesg);
+	
+	exit(code);
+}
+
diff --git a/quit.h b/quit.h
new file mode 100644
index 0000000..344ea1b
--- /dev/null
+++ b/quit.h
@@ -0,0 +1,2 @@
+
+extern void quit(int save, int code);
diff --git a/setpwnam.c b/setpwnam.c
new file mode 100644
index 0000000..1952ecd
--- /dev/null
+++ b/setpwnam.c
@@ -0,0 +1,212 @@
+/* setpwnam.c edit an entry in a password database. */
+
+/*  because I use getpwent(), putpwent(), etc... */
+#define _SVID_SOURCE
+
+#include <sys/types.h>
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <signal.h>
+#include <sys/resource.h>
+#ifdef BSD43
+#include <sys/file.h>
+#endif
+#include <paths.h>
+
+#include "setpwnam.h"
+
+extern int errno;
+
+typedef int boolean;
+#define false 0
+#define true 1
+
+#define PASSWD_FILE	_PATH_PASSWD
+#define PTMP_FILE	_PATH_PTMP
+#define PTMPTMP_FILE	_PATH_PTMPTMP
+
+static int copy_pwd (struct passwd *src, struct passwd *dest);
+static char *xstrdup (char *str);
+static void pw_init(void);
+
+/*
+ *  setpwnam () --
+ *	takes a struct passwd in which every field is filled in and valid.
+ *	If the given username exists in the passwd file, his entry is
+ *	replaced with the given entry.
+ */
+int setpwnam (struct passwd *pwd)
+{
+    FILE *fp;
+    int x, save_errno, fd, ret;
+    struct passwd *entry;
+    boolean found;
+    struct passwd spwd;
+    int oldumask;
+
+    /*  getpwent() returns a pointer to a static buffer.
+     *  "pwd" might have some from getpwent(), so we have to copy it to
+     *  some other buffer before calling getpwent().
+     */
+    if (copy_pwd (pwd, &spwd) < 0)
+	return (-1);
+
+    oldumask = umask(0);   /* Create with exact permissions */
+    pw_init();
+
+    /* sanity check */
+    for (x = 0; x < 3; x++) {
+        if (x > 0) sleep (1);
+	fd = open (PTMPTMP_FILE, O_WRONLY|O_CREAT, 0644);
+	if(fd == -1) {
+	    perror(PTMPTMP_FILE);
+	    umask(oldumask);
+	    return (-1);
+	}
+	ret = link(PTMPTMP_FILE, PTMP_FILE);
+	unlink(PTMPTMP_FILE);
+	if(ret == -1)
+	    close(fd);
+	else
+	    break;
+    }
+
+    umask(oldumask);
+    if (ret == -1) return (-1);
+
+    /* ptmp should be owned by root.root or root.wheel */
+    if (chown (PTMP_FILE, (uid_t) 0, (gid_t) 0) < 0)
+	perror ("chown");
+
+    /* open ptmp for writing and passwd for reading */
+    fp = fdopen (fd, "w");
+    if (! fp) goto fail;
+
+    setpwent ();
+
+    /* parse the passwd file */
+    found = false;
+    while ((entry = getpwent ()) != NULL) {
+        if (! strcmp (spwd.pw_name, entry->pw_name)) {
+	    entry = &spwd;
+            found = true;
+        }
+        if (putpwent (entry, fp) < 0) goto fail;
+    }
+    if (fclose (fp) < 0) goto fail;
+    close (fd);
+    endpwent ();
+
+    if (! found) {
+	errno = ENOENT; /* give me something better */
+	goto fail;
+    }
+
+    /* we don't care if we can't remove the backup file */
+    unlink (PASSWD_FILE".OLD");
+    /* we don't care if we can't create the backup file */
+    link (PASSWD_FILE, PASSWD_FILE".OLD");
+    /* we DO care if we can't rename to the passwd file */
+    if (rename (PTMP_FILE, PASSWD_FILE) < 0)
+	goto fail;
+    /* finally:  success */
+    return 0;
+
+ fail:
+    save_errno = errno;
+    if (fp) fclose (fp);
+    if (fd >= 0) close (fd);
+    endpwent ();
+    unlink (PTMP_FILE);
+    errno = save_errno;
+    return (-1);
+}
+
+#define memzero(ptr, size) memset((char *) ptr, 0, size)
+static int failed;
+
+static int copy_pwd (struct passwd *src, struct passwd *dest)
+{
+    /*  this routine destroys abstraction barriers.  it's not portable
+     *  across systems, or even across different versions of the C library
+     *  on a given system.  it's dangerous and evil and wrong and I dispise
+     *  getpwent() for forcing me to write this.
+     */
+    failed = 0;
+    memzero (dest, sizeof (struct passwd));
+    dest->pw_name = xstrdup (src->pw_name);
+    dest->pw_passwd = xstrdup (src->pw_passwd);
+    dest->pw_uid = src->pw_uid;
+    dest->pw_gid = src->pw_gid;
+    dest->pw_gecos = xstrdup (src->pw_gecos);
+    dest->pw_dir = xstrdup (src->pw_dir);
+    dest->pw_shell = xstrdup (src->pw_shell);
+    return (failed);
+}
+
+static char *xstrdup (char *str)
+{
+    char *dup;
+
+    if (! str)
+	return NULL;
+    dup = (char *) malloc (strlen (str) + 1);
+    if (! dup) {
+	failed = -1;
+	return NULL;
+    }
+    strcpy (dup, str);
+    return dup;
+}
+
+#ifdef NO_PUTPWENT
+
+int putpwent (const struct passwd *p, FILE *stream)
+{
+    if (p == NULL || stream == NULL) {
+	errno = EINVAL;
+	return (-1);
+    }
+    if (fprintf (stream, "%s:%s:%u:%u:%s:%s:%s\n",
+		 p->pw_name, p->pw_passwd, p->pw_uid, p->pw_gid,
+		 p->pw_gecos, p->pw_dir, p->pw_shell) < 0)
+	return (-1);
+    return(0);
+}
+
+#endif
+
+static void
+pw_init()
+{
+	struct rlimit rlim;
+
+	/* Unlimited resource limits. */
+	rlim.rlim_cur = rlim.rlim_max = RLIM_INFINITY;
+	(void)setrlimit(RLIMIT_CPU, &rlim);
+	(void)setrlimit(RLIMIT_FSIZE, &rlim);
+	(void)setrlimit(RLIMIT_STACK, &rlim);
+	(void)setrlimit(RLIMIT_DATA, &rlim);
+	(void)setrlimit(RLIMIT_RSS, &rlim);
+
+	/* Don't drop core (not really necessary, but GP's). */
+	rlim.rlim_cur = rlim.rlim_max = 0;
+	(void)setrlimit(RLIMIT_CORE, &rlim);
+
+	/* Turn off signals. */
+	(void)signal(SIGALRM, SIG_IGN);
+	(void)signal(SIGHUP, SIG_IGN);
+	(void)signal(SIGINT, SIG_IGN);
+	(void)signal(SIGPIPE, SIGQUIT);
+	(void)signal(SIGQUIT, SIG_IGN);
+	(void)signal(SIGTERM, SIG_IGN);
+	(void)signal(SIGTSTP, SIG_IGN);
+	(void)signal(SIGTTOU, SIG_IGN);
+
+	/* Create with exact permissions. */
+	(void)umask(0);
+}
diff --git a/setpwnam.h b/setpwnam.h
new file mode 100644
index 0000000..2c37cc2
--- /dev/null
+++ b/setpwnam.h
@@ -0,0 +1,5 @@
+
+#include <pwd.h>
+
+extern int setpwnam (struct passwd *pwd);
+
diff --git a/utils.c b/utils.c
new file mode 100644
index 0000000..2f3ee43
--- /dev/null
+++ b/utils.c
@@ -0,0 +1,167 @@
+
+/* utils.c - common utilities */
+ 
+#include <stdio.h>
+#include <ctype.h>
+#include <stdarg.h>
+#include <string.h>
+#include <stdlib.h>
+#include <syslog.h>
+#include <errno.h>
+
+#include "utils.h"
+#include "mbox.h"
+#include "config.h"
+
+//extern  int     sys_nerr;
+
+/* Send the prompt */
+ 
+void prompt(void)
+{
+	printf("%s@%s\nCurrent message %i of %i\n=> ", callsign, hostname, current, messages);
+}
+
+/* Prompt for email forwarding */
+void getaddy(char *forward)
+{	
+	char email[79];
+	getstr(email, 79, "What email address do you want to autoforward mail to? This must be a full\nvalid email address. Example: n1uro at n1uro.com or just hit ENTER to clear.\n");
+	strcpy(forward, email);
+}
+
+/* Prompt for name */
+
+void getname(char *uname)
+{
+	char nam[81];
+
+rename:
+	getstr(nam, 80, "Enter your name (? for help): ");
+	
+	if (!strcmp(nam, "?")) {
+		printf("The name entered will be used in the From: header of the messages you send.\n");
+		printf("It will also be shown in finger queries and a number of other places.\n");
+		printf("It is usually set to your full name, but you may also use a nickname\n");
+		printf("your friends know.\n");
+		goto rename;
+	}
+
+	if (strlen(nam) > 30) {
+		printf("The length of the name is limited to 30 characters.\n");
+		goto rename;
+	}
+	
+	if (anyof(nam, "=<>()|:;!\\\",")) {
+		printf("Characters = < > ( ) | : ; ! \\ \" , are not allowed.\n");
+		goto rename;
+	}
+		
+	if (anycntrls(nam)) {
+		printf("Control characters are not allowed.\n");
+		goto rename;
+	}
+
+	strcpy(uname, nam);
+}
+
+/* Get a string from the user, with maximum length limit */
+
+void getstr(char *str, int len, char *prompt)
+{
+	char *p;
+
+	printf("%s", prompt);
+	fflush(stdout);
+	fgets(str, len, stdin);
+
+	/* Strip CR */
+	p = strchr(str, '\n');
+	if (p != NULL)
+		strcpy(p, "");
+
+}
+
+/* Convert a string to upper case */
+
+char *strupr(char *s)
+{
+	char *p;
+
+	if (s == NULL)
+		return NULL;
+	
+	for (p = s; *p != '\0'; p++)
+		*p = toupper(*p);
+		
+	return s;
+}
+
+/* Convert a string to lower case */
+
+char *strlwr(char *s)
+{
+	char *p;
+
+	if (s == NULL)
+		return NULL;
+	
+	for (p = s; *p != '\0'; p++)
+		*p = tolower(*p);
+		
+	return s;
+}
+
+/* Check if any of the characters in the two strings match. */
+
+int anyof(char *s1, char *s2)
+{
+	while (*s1)
+		if (index(s2, *s1++))
+			return 1;
+	return 0;
+}
+
+/* Check if there are any control characters in there. */
+
+int anycntrls(char *s1)
+{
+	while (*s1)
+		if (iscntrl(*s1++))
+			return 1;
+	return 0;
+}
+
+/* Crash, log the reason */
+ 
+void panic(const char *fmt, ...)
+{
+	va_list args;
+	
+	va_start(args, fmt);
+	vprintf(fmt, args);
+	putchar('\n');
+	syslog(LOG_NOTICE, fmt, args);
+	va_end(args);
+
+	exit(1);
+}
+
+/* Report an error returned from a system call. */
+
+
+void syserr(const char *fmt, ...)
+{
+	int e = errno;
+	va_list args;
+	
+	va_start(args, fmt);
+	vprintf(fmt, args);
+	va_end(args);
+	
+/*	routine changed by VE3TOK	*/
+	printf("Error number: %d\n", e);
+	perror("The following error occured: ");
+
+}
+
diff --git a/utils.h b/utils.h
new file mode 100644
index 0000000..183113c
--- /dev/null
+++ b/utils.h
@@ -0,0 +1,15 @@
+
+extern void prompt(void);
+
+extern void getname(char *uname);
+extern void getstr(char *str, int len, char *prompt);
+
+extern char *strupr(char *s);
+extern char *strlwr(char *s);
+extern int anyof(char *s1, char *s2);
+extern int anycntrls(char *s1);
+
+extern void panic(const char *fmt, ...);
+extern void syserr(const char *fmt, ...);
+/* n1uro */
+char callsign[20];

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-hamradio/axmail.git



More information about the pkg-hamradio-commits mailing list