GUIDE to
SAM Kernel and Application
Updated 2020-10-18

Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2010, 2011, 2012,
2014, 2015, 2018, 2020 Joseph Rosevear



1.  A short table of references in this distribution.

2.  What is this?

3.  Some terminology.

4.  Installing SAM.

5.  Running SAM.

6.  Using SAM.

7.  About SAM menus.

8.  Special variables.

9.  There is a nuisance you may encounter.

10.  SAM's temporary and scratch directories.

11. Shells used.

***


1.  Informative files in this distribution.

$sam_root        $sam          $sam_distro
---------        --------      -----------
COPYING          GUIDE-K       CONTENTS
ENV-NOTE         README-K
GUIDE
README
TIPS

$sam_root is the root of the installation.

$sam is $sam_root/opt/SAM_modules/kernel.

$sam_distro is $sam_root/opt/SAM_modules/main.



2.  What is this?  This is a distribution of SAM Kernel and Application
and was written by me, Joseph Rosevear.  See file COPYING in this
distribution for a statement of the license agreement.  (Refer to the
COPYING file in the "main" module.)


3.  Some terminology.  This is a distribution of SAM Kernel and
Application which is also known as "SAM" (upper case).  SAM uses
variable "sam" (lower case) which is set to the installed location of
the SAM kernel.  The SAM kernel is provided in a single directory.  (I
will alternately call directories "dirs".  Dirs which are modules I
will sometimes call "modules".)

The SAM application is also known as An Application of SAM for
GNU/Linux Slackware or SAM-GLS.  It consists of one required module,
main.  There are other optional modules.  each of which lives in its
own dir.  The module main has symbolic links to the other modules which
make it appear as the root of the whole installed distribution.

SAM uses a symbolic link, SAM->SAM_modules/main.  SAM also uses a
variable "sam_distro" which points to the location of this link (using
its full path).  Considering this and the above paragraph, we can
therefore refer to the whole distribution as SAM or $sam_distro.  (I
prefer to use $sam_distro.)

SAM uses a symbolic link SAM/sam->../kernel.  We can therefore refer
to the kernel as SAM/sam or $sam.  (I prefer to use $sam.)


4.  Installing SAM.

First I need to tell you about SAM archives.  Previously I used
traditional Slackware package archives that end with ".tgz".  (I think
that normally the word "archive" is not used for Slackware package
archives.  They are just called "packages".) The names of the archives
were based on dir name in SAM_modules combined with a date string.  For
example a kernel package archive could be named

   sam-kernel-100822aa.tgz

This is what I did previously.  I have abandoned that method in favor
of something more simple, and I no longer use Slackware packages.  The
way that SAM works is unusual, and so little benefit comes from use of
Slackware packages for it.  In fact, this would perhaps be misleading. 
Instead I use a single tar ball and some simple installation
instructions that the user performs manually.

Also, to keep things simple, I have made two more changes:  (1) I no
longer use separate archives for the different modules, and (2) the
b-files are already in place and ready to use in dir $sam_root.  Legacy
files including b-files can be found in $sam_distro/leg_tips

SAM_modules contains these dirs:

These modules are required:

   kernel      The SAM Kernel.
   main        This SAM-GLS package is required, the
                others are optional.

These are optional.

   example     Large set of examples of use of SAM.
   tool        Tools for SAM.  Recommended.
   pkg_tool    Slackware package tools. (Probably not needed now that I
                don't use Slackware packages.)

This is the structure of SAM after installation.  The indentation shows
the directory structure.  (Note that SAM could be configured and
installed with a different directory structure, however this
distribution requires the current structure.)

   <root of SAM>     (You may name this dir anything that you want, and
                     put it anywhere you want--such as at the root of a
                     flash drive.)
      opt
         SAM         (SAM->SAM_modules/main)
         SAM_modules
            example  (Optional.)
            kernel   (Required.)
            main     (Required.)
            pkg_tool (Optional.)
            tool     (Optional, but recommended.)

The b-files take care of some things for you.  A b-file called bprofile
is important, because it takes care of two critical variables.  These
are sam_temp_base and sam_set_version.  They need to be set and
exported.  Another variable, glos, should be unset.  bprofile manages
these variables, and is the current and best way, although this is a
new method that comes after a long tradition of using ~/.bash_profile
for this purpose.  See $sam_root/TIPS for more information
about b-files and variables.

Note how SAM differs from traditional software; you should not change
your PATH variable to include SAM executables.  Neither should you put
SAM exectables in dirs that are in your normal PATH.  See the section
below, Running SAM, to learn how to run SAM.


5.  Running SAM.

The word "run" is a little misleading here.  There is code that is run
to begin SAM and to end SAM.  This code runs in the usual sense.  But
in between beginning and ending nothing is running, not even a daemon
or a process in the background.  SAM is similar to an old piece of
software for the Commodore 64 called the "DOS Wedge" in this way.  It
gets the work done not by running, but by changing how things run.  SAM
does this by manipulating the environment.  It changes the PATH
variable and other variables, and it sets and unsets variables and
functions.

I needed to explain this, but I will not talk about it anymore.  I will
use the word "run" in reference to SAM and expect you to understand
what it means.  Here, then, is what you need to know about "Running
SAM":

There are four traditional scripts that participate in running SAM. 
They are "begin", "bree", "breekit" and "bstart".  And there is one new
script that is still earning its way in the world: buser.  You can find
all six of these (and I think a few others) in the b-files package. 
Each has a different purpose.  For example, enter

   <root of SAM>/begin

to start SAM in the normal way.  It can be used when SAM is not
running, or you can use it again after you have already started SAM. 
You will know that SAM is running by the changed prompt.  (SAM has a
two-line prompt.) To exit from SAM enter "bye" or "exit".

Note in the above that <root of SAM> depends on where you have
installed the b-files package.

Each of the b-files can be used directly by naming its full path, as I
have shown above, and that is fine to do.  However, to save some typing
you can alternately copy them to or make symlinks to them in your home
directory (or anywhere).  If you put them in your home direcotory, then
you can invoke them with ~/<b-file>.  Copying them to your home
directory (or to any directory or even to new names in the same
directory) gives you the benefit of having a copied file to customize
without losing the original.

SAM can be run by an ordinary user or by root, but root should not use
bree or breekit, as these scripts provide root authority.  Root already
has root authority, so something confusing would probably result.

Note that the b-files in package b-files are the new easy-cheesy
b-files.  The original b-files, which require a little different, and
lengthier, SAM installation (and cannot be used from a flash drive
plugged into an un-prepared Slackware host) are still available for
reference or use in their traditional locations.  "bree" and "bstart"
are found in opt/SAM, and "begin" and "breekit" are in opt/SAM/tips.

Here are explanations of the use of "begin", "bree", "breekit" and
"bstart":


   begin          Uses bstart to run SAM for ordinary users and root.

   bree           Runs SAM again from an environment in which it is
                  already running.  The new instance becomes root and
                  inherits the previous environment.  It should be run
                  by an ordinary user (not root).

   breekit        Uses bstart to run SAM, and then bree to run SAM
                  again (recursively) as root.  It should be run by an
                  ordinary user (not root).

   bstart         Runs SAM for ordinary users and root.


6.  Using SAM.

After invoking SAM you will have a menu on your screen.  You can scroll
up and down with the up and down arrows.  (You are actually using the
"less" command.) Pressing "q" returns you to the command prompt.  Enter
"menu" to display the menu again.

Enter commands from the menus to do the things described by the menus.

This (above) may confuse some users.  Some people expect a menu to have
automation built in so that you click with a mouse and something
happens.  SAM's menus don't work that way.  I insist that they are
still menus, but I admit that they are not "traditional" menus.

Use "exit" to leave SAM.

Use "bye" to leave a menu and return to the previous one.  When there is no
previous menu "bye" will take you all the way out of SAM.

Use ";" to separate commands on one line.  This is a feature of Bash,
not of SAM, but it works well in SAM.


7.  About SAM menus.

A menu for sam is a file named "menu.dat".  Make one and put it in a
directory, and it will be displayed by the use of the command

   menu

when it is the "local" menu.  To make a menu local (and the directory
that it is in) use the "bound" command.

I will illustrate with an example, but first I need to mention my use
of the term "local".  That is my term.  I invented it.  When using SAM
a directory can be "current" and it can also be "local".  These two are
independent.

A directory is current when you are in it.  You go into a directory by
using "cd".  That is nothing new.  A directory is "local" when you
"bound" to it.  Here is an important concept:

   I will often refer to a menu as being local.  That is just a short
   way of saying "the directory is local, and it has a menu that is
   intended to describe the available commands in that directory".

   I won't explain this again.  When I talk about a menu being local,
   please understand it to mean what I have explained above.

Here is an example (you will need to be in Slackware 10.0 or more
recent.  See file opt/SAM/tips/README for more information.):

   export sam_temp_base=/tmp
   export sam_set_version=2
   export sam_bplace=<path to root of SAM>
   export sam_distro=$sam_bplace/opt/SAM
   $sam_bplace/bstart
   echo test > /tmp/menu.dat
   bound /tmp
   bye
 
See opt/SAM/tips/README to understand the first two lines. The third
line tells where to find the b-files.  The fourth line tells where to
find SAM.  The fifth line runs SAM.  You will probably need to enter
"q" to leave the menu viewer (less), and you will probably need to do
this twice in this example.  Then next line makes a menu that contains
the word "test".  That is not very useful, but it gets us started. 
Then the example makes the new menu local ("bound /tmp" does this). 
The "menu" command causes the menu to be displayed, and "bye" will exit
SAM.

Before I explain what this does, I want to show you another, simpler
way to do almost the same thing:

   <path to root of SAM>/begin
   echo test > /tmp/menu.dat
   bound /tmp
   bye

If you examine scripts bstart and begin you will see that the two ways
are similar, but not the same.  I favor begin over bstart.  In fact, I
practically never use bstart.  You choose.

Here (between vvv and ^^^) is the menu that you will see after entering
"bound /tmp" (by the first way):

vvv
/tmp

local  {
 COMMAND       DESCRIPTION
test

global {
 COMMAND       DESCRIPTION
Builtin     --
    exit       Closes the current shell.  If SAM was started in the
                current shell, then exit will terminate SAM.
in $sam     --
   about       Menu about the SAM kernel including the following:
               author, documentation, license, ABSOLUTELY NO WARRANTY,
               redistribution.

   bound       Adds $1 to PATH.  This is not inherited by subsequent
               synthetic shells.  Also adds $2 (if any) to PATH.  This
               is inherited.  If $3 is "final", then bye will cause SAM
               to exit.  Use "-" for $2 if needed to define $3.  bound
               will display a menu unless sh_flag is set.

     bye       Causes SAM to leave current menu and return to the
               previous.

    menu       If $1 is blank, displays local and global menus
               otherwise displays these menus for $1.

in $sam_tool--
  anchor       Marks current directory--see away command.  Commands
                cdfar, chang and root automatically do this before
                changing directories.
    away       Changes to last marked directory.
   cdfar       Changes to directory $1.
   chang       Changes to directory named in first line of prompt. 
                (This is the "local" directory.)

checkpkg       Runs Volkerding's installpkg with -warn on $1.  When it
                does this it writes a list of files to
                $env_scratch/.  Then it does some things to check if
                any of those files already exist.  This determines if
                there would be any collisions.

                Note:  You should probably do this (as root, in stage):

                   prepare the package in /usam-d/noyear/apps/<app>/stage
                   make a stage/install/slack-desc file
                   make the package with      makepkg `pwd`/<package.tgz>
                   check the package with     checkpkg      <package.tgz>
                   install the package with   installpkg    <package.tgz>
               
                Then view the package with     pkgtool

    hold       Holds current place in a script by starting a new SAM
                session.  The menu of the new SAM session will be
                unchanged or if $* exist, it will be $*.  Returns to
                previous menu after "exit".

                *******************************************************
                Note that there are two other ways to get behavior
                similar to hold: (1) Reference $sam_distro/go/sam1-5 to
                open a SAM menu.  Use a last arg of "final" to cause
                the return to the previous menu.  (2) Like (1), but add
                a payload to final like this "final; `cat<<done

                blah;
                blah;
                blah;
                bye
                done`"

                Be careful to not a line with a ; that doesn't need
                one, such as "if [ blah ]; then".

                The second way is good to give sudo controlled access
                to trusted users for SAM commands that need root
                authority.  The final "bye" (augment if needed) is
                meant to end the session.  Note, this is not even close
                to a secure way to run a command.  A simple ctrl-C will
                end the script in the middle and leave the user access
                to root.
                *******************************************************


    home       Does cd $HOME

      lc       Means "ls in color".  It does "ls $LS_OPTIONS".

    love       Sets the sh_flag to turn off menus.  It does this after
                first running hello to isolate the current synthetic
                shell.  It also changes the sam_symbol from ":)" to
                ":x" to remind you that menus are off.

     pda       Works with pdb.  Use without args to see usage.  Use pda
               first, then pdb.  The pair work together to copy a file
               from an old year to the current.

     pdb       Works with pda.  Use pda first, then pdb.  You may have
               to copy $sam_tool/pda.f to ~, then use "bound $level ~"
               to invoke it.  Use without args to see usage.

    root       Does cd /

     sub       Makes $level/$1 local.  In other words, it goes to
               sub-menu $1.


               *** tools for pdata system ***                


     dog       Gives a dog and pony show.  Sort of.  Works with
               net_or_rem and splurge9.  Together they use file
               $env_handy/pony.spl as a skeleton to make, using
               splurge9 and $1, a text file with pictures (thus "dog
               and pony").  It displays this show using net_or_rem.

               All you do is:

               (1) Provide an ordinary text file (at
               $level/data/dog/$1.dat$2) that contains correct html for
               including pictures.  Other html is OK, but not needed. 
               File $sam_tool/pony.spl provides the <pre> and </pre>
               and html and body tags.  You can make this file with:

                  <name>

               when in "pdata".  Try this to see an example:

                  ex_dog

               (2) It is suggested you provide the pictures at
                $level/data/picture/*, but not required.

               (3) Invoke like this:

                  dog $1

               or

                  dog $1 $2

               where $2 is a version number.

     map       Opens the maps for $1.* if available.  Look for "(map)" in
               the menus.  This command often gives extra information
               for an existing menu item.

               Notes:  Maps are opened with xv.  First map should be
               $1.jpg.  Second map, $1.jpg2, etc.

    ment       Makes new file $level/$1 which will open a personal data
               file when invoked.  You must also make the entry
               yourself in the menu.dat file.

                About the use of the commands made by ment:
                 1.  <command> <numeral>
                     This will open file <command>.dat<numeral>
                      which allows you to view archived files.
                 2.  <command> - <parameter> This will open file
                      <command>.dat using the passed parameter such as
                      -overwrite.  Handy for editing files in overwrite
                      -mode.
            
   emenu       Uses texed to edit $level/menu.dat, or if there is one
                argument, $1/menu.dat.
   mshow       Shows all the files $level/data/$1.dat*
                It is helpful to know the family of files.
    mzit       Makes a starter file $level/menu.dat if it doesn't
                already exist.
    msub       Makes file $1.sam that will invoke "sub $1" from a .sam
                script.  Also, if dir $1 does not exist, makes $1 and
                uses mzit on it.
 picture       Opens the picture $1.* if available.  $1 is normally a
                digit like 1, 2, etc.  Look for picture references in
                the texts available in pdata.  They will look like
                this, "see picture 1".  In response to this information
                you enter "picture 1".  This will cause the file
                data/picture/1.* to be opened in xv.

prn2file       This is needed by CUPS in order to print to a file. 
                See instructions in prn2file for how to setup.  Once
                setup, print to a file with "lpr -Pfile".  prn2file was
                not meant to be used directly.

 sel_prn       Does "export printer=$1".  Or if there are no arguments,
                then it echos the value of $printer.  Use this to learn
                the value of "printer" or to define and export
                "printer".  I've begun to use variable printer in tools
                that print.

This menu is hosted by...

SAM Kernel and Application

Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2010, 2011, 2012,
2018 Joseph Rosevear.  SAM comes with ABSOLUTELY NO WARRANTY; for
details type

   love; about; warnty; bye; bye

This is free software, and you are welcome to redistribute it under
certain conditions; for details type

   love; about; redist; bye; bye
^^^

You will notice that this menu is long.  Sorry about that.  This is the
current state SAM as I use it.

If you examine the menu, you will see that it has two parts called
"local" and "global".  The global part describes commands that are
intended to be "globally" available.  The term "global" here is mine. 
It means that the commands are always available for any choice of local
menu.

You will also see that the global part is the long part.

The first line of the menu

   /tmp

shows the directory that is now local.  This tells you that "/tmp" has
been added to the PATH variable and hash has been run so that the
commands of /tmp are now available.  We didn't put any commands in
/tmp.  I suggest that you try putting a command or two there if you are
unfamiliar with the use of hash and the PATH variable.

Here is what I get when I look at the PATH variable ("echo $PATH"):

   /mnt/150605aa2/opt/SAM/sam:/tmp/temp1:/mnt/150605aa2/opt/SAM/tool:/usr/local/bin:/usr/bin:/bin:/usr/games:/usr/lib/kde4/libexec:/usr/lib/qt/bin:/usr/share/texmf/bin:/tmp

If you look at this long line you will see that it contains some new
elements that weren't in PATH before you ran SAM.  I'll name describe
them here:

   /mnt/150605aa2/opt/SAM/sam   This is the sam kernel.  These commands
                                are needed by SAM.

   /tmp/temp1                   This is the location of the temporary
                                directory ($sam_temp_dir) currently in
                                use by SAM.

   /mnt/150605aa2/opt/SAM/tool  This is the location of SAM's tool
                                package, an optional package that adds
                                commands to the global menu.

   /tmp                         This corresponds to the command "bound
                                /tmp" that you entered.  This
                                shows the usefulness of SAM.  If there
                                were commads at /tmp that you wished to
                                use, they would now be in the PATH and
                                therefore available.  Ideally, the file
                                /tmp/menu.dat would describe these
                                commands.

The rest of the menu describes what is intended to be the commands that
are available locally and globally through SAM.  The commands that are
intended to be available locally are in file /tmp/menu.dat, because
/tmp is the local directory.

The commands that are intended to be available globally are described
in $sam/menu.dat, $sam_tool/menu.dat, plus the "exit" command which is
actually a built-in shell command.

After the above information you are still missing something about
menus.  "How do I format a menu correctly and how do I make my menu
come up when SAM is run?"  I can address both of these by referring
you to these two dirs:

   <root of SAM>/opt/SAM/tips
   <root of SAM>

I need to explain that the first dir is no longer in use, except for
reference.  I'm in the process of trasitioning the documentation and
the code, so in the meantime, I'll keep the first dir.

These dirs each contain a sam-start directory.  You don't have to have
a sam-start directory, but it is meant to be a convenient way to make a
menu that comes up automatically when SAM is run.

The sam-start directory can contain any commands that you wish to put
in it.  These can be scripts, compiled code, or even function
definitions.  Give your function definition files a name that ends in
".sam" and they will be automatically made available at the appropriate
time just like an ordinary commands.  (You will need also to include
the line "#OK SAM" as the first line of the function definition.)

You can use the menu.dat file in /opt/SAM/tips as an example or just
use (handy) mzit command which is in the sam-tool package of this
distribution.

8.  Special variables.

These variables can be used to control the behavior of SAM.  Set them
anyplace and anytime:

export sam_batch=batch

  Exporting sam_batch with value of batch (or anything) will cause SAM
  to be run in a batch mode.  In this mode it will not give you
  interactive behavior.  Sometimes interrupting a shell script results
  in an interactive shell opening at the point where the script
  stopped.  Often this is not desired.  Use this variable to prevent
  this behavior.

sh_flag=sh

   Export this or just set it.  When it has a value not equal to "" it
   prevents the automatic displaying of menus by SAM.  Menus can still
   be dispalyed manually by the "menu" command.


These variables also control the behavior of SAM.  Normally they should
be set and exported from inside $sam_env:

export sam_menu=<alternate menu executable>

   You would export this to change the behavior of
   $sam_distro/sam/menu, the script which displays SAM's menus.

export sam_message=<executable that you wish to run upon exiting SAM>

   Normally you export this to change the message that SAM displays
   upon exiting.  You would then set sam_message to the path of an
   executable that displays a message.

   The default is to use SAM's prepared message.  This variable is used
   by $sam_distro/sam/sam_core.

export sam_view=<alternate menu viewer>

   You would export this to change the viewer which is used by
   $sam_distro/sam/menu to display menus.

   The default viewer is "less".

There are other variables that are important to SAM but are normally
dealt with by your "~/.bash_profile".  Read about them in /tips/README
in this package ($sam_distro/tips/README).


9.  There is a nuisance that you might encounter.  This nuisance
happens when files in $sam_temp_dir (which points to the current temp
for SAM) gets files in it that cannot be written to.  Say for example
that you have a temp dir at ~/temp1, but you get a file in it that
belongs to root.

When this happens you will need to change to root, go to ~/temp1 (or
temp2, etc) and change the ownership of the files back to the user (not
root). Or you can leave SAM, clean out the $sam_temp_dir's, and try
again.


10.  SAM's temporary and scratch directories.

This tells the scheme for SAM's temporary and scratch directories.


$sam_temp_base    You can set sam_temp_base to anything you want, but
                  $sam_root/bprofile included with this distribution
                  sets it to:

                     /tmp/`whoami`

$sam_temp_dir     You can set sam_temp_dir to anything you want, but
                  $sam_distro/go/sam included with this distribution
                  sets and exports it like this:

                     export sam_temp_dir=$sam_temp_base/temp${1}

temp<n>           temp1 - temp<n> are made by this line in
                  $sam/sam_core:

                     mkdir --parents $sam_temp_dir

                  Note that (in this distribution) this will also make
                  $sam_temp_base if it does not already exist.

$env_scratch      I believe (but I'm not sure) that you can set
                  env_scratch to anything you want, but
                  $sam_root/sam_env included with this distribution
                  sets and exports it like this:

                     export env_scratch=$sam_temp_base/scratch

scratch           Make scratch any way you like, but in this
                  distribution scratch is made by this line in
                  $sam_root/brc:

                     mkdir --parents $sam_temp_base/scratch

                  Note that this will also make $sam_temp_base if it
                  does not already exist.

Note that the number of temp<n> directories is limited mainly by the
way in which SAM is configured.  In the current distribution the
maximum number of directories is configured by the way in which
$sam_distro/bstart invokes $sam_distro/go/sam1.  In particular, the
maximum is $1.

temp<n> are known as $sam_temp_dir.


11.  Shells used


SAM uses #!/bin/sh in all scripts except in this case:

   Scripts that are to be sourced have no line beginning "#!".

I spent some time trying out SAM in Ubuntu.  In Ubuntu /bin/sh is a
link to dash.  SAM should work OK in Ubuntu if you first change that
link to point instead to the (traditional) bash.  Also you may need to
have a real root account.  There is a change you can make in Ubuntu to
do this.  I recommend it.  (Do "sudo passwd root" to get a real root. 
If you change your mind do "sudo passwd -l root" to lock root again.)

One script (sam_core) in the kernel package has code that opens
additional shells.  This is done using "/bin/bash".  I chose
"/bin/bash" over "/bin/sh", because I wanted to use the --rcfile
option.  Using this option let me write better code, so I did it.  This
works in Ubuntu, but functionality in Ubuntu was not the reason for the
choice.
