/* Create master sequence
 * This program is intended to be called from Suntan Special
 *
 * Description
 *   This command guides the user to create a Suntan Special master sequence
 *   suitable for the operating system installed and purpose of installing
 *   the whole suite of fixes and applications on the computer.
 *
 * Copyright (C) 2024 Blonde Guy
 * All Rights Reserved
 */

productName = 'Create master sequence'
productDate = '2024-12-03 10:00:00'
productCategory = 'Configuration'

originalDir = Directory()
parse arg appsDir
cr = d2c(13)
suntanDir = cdglobal('SuntanDir')

call LogCdi productName

message = productName || cr || cr || cr ||,
          "This command creates and runs a Suntan Special master sequence",
          "suitable for installing",
          "the whole suite of fixes and applications on the computer." || cr || cr ||,
          "Press OK to continue"
reply = MessageDialog(productName, 1, message)

/* ProbePlatform -- detect the following
   myOS - operating system Warp4, MCP, eCS, ArcaOS
   myOSVer - operating system version
   isVirtualBox - 1 if running on VirtualBox, 0 otherwise
   mySeq - suggested sequence for that version (or none)
*/
rc = ProbePlatform()
if rc <> 0 then do
   call LogCdi "Error" rc "probing platform"
   return 1
end

message = "Operating system detected" || cr || cr || cr ||,
          "This is the detected environment" || cr ||,
          "Operating System:" myOS || cr ||,
          "Version:" myOSVer || cr ||,
          "VirtualBox:" isVirtualBox || cr ||,
          "Press OK to continue."
reply = MessageDialog(productName, 1, message)

if myOS = '' then do
   call LogCdi "No operating system was detected."
   return 1
end

if mySeq = 'none' then do
   call LogCdi mYOS "is not supported"
   return 1
end

if myOS = 'Warp4' then do
   message = "Warp 4 was detected" || cr || cr || cr ||,
             "There are two sequences to handle Warp 4. Warp4.seq uses features only",
             "available to Software Choice or Passport Advantage",
             "subscribers. Freewarp.seq uses only freely available features for",
             "Warp 4 license holders."
   mySeq = radiolist("Warp 4 sequence", message, "Enter sequence", "!freewarp.seq", "warp4.seq", "None")
   if mySeq = "None" then do
      call LogCdi "User chose None, so ending application."
      return 1
   end
end

message = "Platform Sequence" || cr || cr || cr ||,
          "For this computer running" myOS || ", the platform sequence",
          "will be" mySeq || ". Press OK to accept this name or Cancel",
          "to exit this application."
reply = MessageDialog(productName, 5, message)
if reply = "Cancel" then do
   return 1
end

hostname = cdglobal('hostname')
if hostname = '' then do
   hostname = value('hostname',,'os2environment')
end
message = "Computer hostname" || cr || cr || cr ||,
          "Enter the hostname of this computer. A sequence with this name",
          "will be created. The name must use only characters compliant",
          "with OS/2 file names.",
          "Enter a blank name to terminate this command."
hostname = query(productName, hostname, message, 'Text')
if hostname = '' then do
   call LogCdi "User terminated command with a blank hostname."
   return 1
end

username = value('USER',,'OS2ENVIRONMENT')
if username = '' then do
   username = cdglobal('username')
end
else do
   call SetSetting 'username', username
end
password = cdglobal('password')
message = "Username/Password" || cr || cr || cr ||,
          "Suntan Special will use a stored password and username to",
          "configure the system and applications. The username is" username,
          "and the password is" password || ". Press OK to keep these",
          "values, or press Cancel to enter new ones."
reply = MessageDialog(productName, 5, message)
if reply = "Cancel" then do
   username = QuerySettings('username', 'Query')
   password = QuerySettings('password', 'Query')
end

message = "The following sequences will be executed after" mySeq "has",
          "completed."
sequenceList = checklist("Additional Sequences", message, "check to install", 'ArcaNoae.seq', 'apps.seq', 'comapps.seq', 'games.seq', 'dev.seq', 'cleanup.seq')

extraSeq = ''
message = "User Sequence" || cr || cr || cr ||,
          "Specify an optional User-written sequence to execute after the",
          "Suntan Special sequences are complete. This is optional. Leave the",
          "field blank to skip adding a User-written sequence."
extraSeq = query(productName, extraSeq, message, 'File')
if extraSeq <> '' then do
   call LogCdi "Adding User-written sequence" extraSeq
   extraDir = strip(filespec('Drive', extraSeq) || filespec('Path', extraSeq), 'Trailing', '\')
   if extraDir <> suntanDir then do
      if stream(extraSeq, 'c', 'query exists') <> '' then do
         address cmd '@copy' extraSeq suntanDir '> nul'
         call LogCdi "copied" extraSeq "to" suntanDir
      end
      else if extraDir = '' then do
         if stream(suntanDir || '\' || extraSeq, 'c', 'query exists') = '' then do
            call LogCdi "warning:" extraSeq "does not exist in" suntanDir
         end
      end
   end
   extraSeqname = ''
   if extraSeq <> '' then do
      extraSeqname = filespec('Name', extraSeq)
   end
end

call writeSequence

message = "Suntan Special is ready to configure this computer." || cr || cr || cr ||,
          "Execute Sequence:" sequenceName || cr ||,
          "Operating System:" myOS "version" myOSVer || cr ||,
          "Platform sequence:" mySeq || cr ||,
          "Press OK to install or Cancel to exit this application."
reply = MessageDialog(productName, 5, message)
if reply = "Cancel" then do
   return 0
end

queue 'ReadConfigFile'
queue 'Set USER=' || username
queue 'WriteConfigFile'
queue 'exit'
call EditConfigSys

call SetSetting 'ShowSuccessDialog', 0
sequenceName = filespec('Name', sequenceName)
call LogCdi "Starting sequence" sequenceName

address cmd '@ Start /min SunBatch START' sequenceName
if rc <> 0 then do
   call LogCdi "Error" rc "Starting SunBatch"
end

call LogCdi "Operation complete"
return 0


writeSequence:

sequenceName = suntanDir || '\' || hostname || '.seq'

if stream(sequenceName, 'c', 'query exists') <> '' then do
   call SysFileDelete sequenceName
   call LogCdi "Deleted old copy of" sequenceName
end

call lineout sequenceName, "; master sequence for" hostname
call lineout sequenceName, ";"
call lineout sequenceName, "set hostname = '" || hostname || "'"

/* set sourceDir='R:\SuntanV6\apps;R:\SuntanV6\dev;R:\SuntanV6\drivers;R:\SuntanV6\fixes;R:\SuntanV6\games;R:\SuntanV6\misc;R:\SuntanV6\server;R:\SuntanV6\system;' || cdglobal('setupDir') */

if isVirtualBox then do
   call lineout sequenceName, "set cdletter = '" || findCDLetter || "'"
   call lineout sequenceName, 'setUSBfloppies 0'
   call lineout sequenceName, 'setUSBcdroms 0' 
end

call lineout sequenceName, "set yumignorerpmdb = '1'"
call lineout sequenceName, "set turboMode = '1'"
call lineout sequenceName, "set ShowSuccessDialog = '0'"
call lineout sequenceName, ";"
call lineout sequenceName, "EXECUTESEQUENCE" mySeq
call lineout sequenceName, "reboot"
call lineout sequenceName, "pause"
call lineout sequenceName, ";"


call lineout sequenceName, "; disable installing Firefox, SeaMonkey and Thunderbird"
appsDir = cdglobal('appsDir')
if stream(appsDir || '\Firefox\firefox.exe', 'c', 'query exists') <> '' then do
   call lineout sequenceName, "set installFirefox='Disabled'"
end
else do
   call lineout sequenceName, "set installFirefox='Enabled'"
end
if stream(appsDir || '\SeaMonkey\seamonkey.exe', 'c', 'query exists') <> '' then do
   call lineout sequenceName, "set installSeamonkey='Disabled'"
end
else do
   call lineout sequenceName, "set installSeamonkey='Enabled'"
end
if stream(appsDir || '\Thunderbird\thunderbird.exe', 'c', 'query exists') <> '' then do
   call lineout sequenceName, "set installThunderbird='Disabled'"
end
else do
   call lineout sequenceName, "set installThunderbird='Enabled'"
end
call lineout sequenceName, ";"

if pos('ArcaNoae.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE ArcaNoae.seq"
   call lineout sequenceName, "reboot"
   call lineout sequenceName, "pause"
end

if pos('apps.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE apps.seq"
end
call lineout sequenceName, "reboot"
call lineout sequenceName, "pause"

if pos('comapps.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE comapps.seq"
end
if pos('games.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE games.seq"
end
if pos('dev.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE dev.seq"
end
call lineout sequenceName, ";"
if extraSeqname <> '' then do
   call lineout sequenceName, 'EXECUTESEQUENCE' extraSeqname
   call lineout sequenceName, ";"
end
if pos('cleanup.seq', sequenceList) > 0 then do
   call lineout sequenceName, "EXECUTESEQUENCE cleanup.seq"
   call lineout sequenceName, ";"
end
call lineout sequenceName, "; end of" hostname "sequence"
call stream sequenceName, 'c', 'close'
return



/* ProbePlatform -- detect the following
   myOS - operating system Warp4, MCP, eCS, ArcaOS
   myOSVer - operating system version
   isVirtualBox - 1 if running on VirtualBox, 0 otherwise
   mySeq - suggested sequence for that version
   
 * scans computer to determine the Operating System and version
 * to help determine which Suntan Special platform sequence to use
 *
 * http://hobbesarchive.com/?detail=/pub/os2/util/system/DMIDECODE_2-12.zip
 *
 * http://www.tavi.co.uk/os2pages/levels.html
 * the executable was renamed to dmidump.exe to fit 8.3 naming as required
 * for use with Warp 4 GA
 */


ProbePlatform:

dmiExe = 'dmidump.exe'
tempDir = value('temp',,'os2environment')
if tempDir = '' then do
   tempDir = cdglobal('tempDir')
end
tempFile = tempDir || '\ps_temp.txt'

call directory tempDir

address cmd '@' originalDir || '\' || dmiExe '>' tempFile
if rc <> 0 then do
   call LogCdi "Error" rc "from DMI Decoder"
   return 1
end

call directory originalDir

verbose = 1
letter = FindBootDrive()

call LogCdi "Scanning DMI..."
call scandmi
call LogCdi "Checking OS version..."
osVersion = os2version()
call LogCdi "Checking OS sys level..."
mySysLevel = OS2sysLevel()
call LogCdi "Version found" vNumber


call getOSname

/* myOS myOSVer
   Warp4 -- freewarp.seq or warp4.seq
   MCP -- mcp.seq
   eCS (version number) -- ecs10.seq;ecs11.seq;ecs12.seq;ecs12r.seq;ecs20.seq;ecs21.seq;ecs22.seq
   ArcaOS (version number) -- ArcaOS50.seq;ArcaOS51.seq
*/


select
   when myOS = 'Warp4' then mySeq = 'warp4.seq'
   when myOS = 'MCP' then mySeq = 'mcp.seq'
   when (myOS = 'eCS') & (myOSVer = '1.0') then mySeq = 'ecs10.seq'
   when (myOS = 'eCS') & (myOSVer = '1.1') then mySeq = 'ecs11.seq'
   when (myOS = 'eCS') & (myOSVer = '1.2') then mySeq = 'ecs12.seq'
   when (myOS = 'eCS') & (myOSVer = '2.2') then mySeq = 'ecs22.seq'
   when (myOS = 'eCS') & (myOSVer = '2.1') then mySeq = 'ecs21.seq'
   when (myOS = 'eCS') & (myOSVer = '2.2') then mySeq = 'ecs22.seq'
   when (myOS = 'ArcaOS') & (myOSVer = '5.0') then mySeq = 'ArcaOS50.seq'
   when (myOS = 'ArcaOS') & (myOSVer = '5.1') then mySeq = 'ArcaOS51.seq'
   otherwise mySeq = 'none'
end

say "sequence for" osName || ":" mySeq
return 0


/* scan dmi */
scandmi:

scan = 0
bscan = 0
cscan = 0
myManufacturer = ''
myProduct = ''
myVersion = ''
mySerial = ''
myUUID = ''
myBIOS = ''
myBIOSdate = ''
myBIOSrevision = ''
myBIOSfirmware = ''
myCPU = ''
do while lines(tempFile) > 0
   myLine = linein(tempFile)
   if scan = 1 then do
      if pos('Manufacturer:', myLine) > 0 then do
         parse var myLine 'Manufacturer:' myMan
         if myManufacturer = '' then do
            myManufacturer = myMan
         end
      end
      if pos('Product Name:', myLine) > 0 then do
         parse var myLine 'Product Name:' myMan
         if myProduct = '' then do
            myProduct = myMan
         end
      end
      if pos('Version:', myLine) > 0 then do
         parse var myLine 'Version:' myMan
         if myVersion = '' then do
            myVersion = myMan
         end
      end
      if pos('Serial Number:', myLine) > 0 then do
         parse var myLine 'Serial Number:' myMan
         if mySerial = '' then do
            mySerial = myMan
         end
      end
      if pos('UUID:', myLine) > 0 then do
         parse var myLine 'UUID:' myMan
         if myUUID = '' then do
            myUUID = myMan
         end
      end
   end
   if bscan > 0 then do
      if pos('Version', myLine) > 0 then do
         parse var myLine 'Version:' myMan
         if myBIOS = '' then do
            myBIOS = myMan
         end
      end
      if pos('Release Date', myLine) > 0 then do
         parse var myLine 'Release Date:' myMan
         if myBIOSdate = '' then do
            myBIOSdate = strip(myMan)
         end
      end
      if pos('BIOS Revision', myLine) > 0 then do
         parse var myLine 'BIOS Revision:' myMan
         if myBIOSrevision = '' then do
            myBIOSrevision = strip(myMan)
         end
      end
      if pos('Firmware Revision', myLine) > 0 then do
         parse var myLine 'Firmware Revision:' myMan
         if myBIOSfirmware = '' then do
            myBIOSfirmware = strip(myMan)
         end
      end
   end
   if cscan > 0 then do
      if pos('Version', myLine) > 0 then do
         parse var myLine 'Version:' myMan
         if myCPU = '' then do
            myCPU = strip(myMan)
         end
      end
   end
   if pos('System Information', myLine) > 0 then do
      scan = 1
   end
   if pos('BIOS Information', myLine) > 0 then do
      bscan = 1
   end
   if pos('Processor Information', myLine) > 0 then do
      cscan = 1
   end
end
call stream tempFile, 'c', 'close'
call SysFileDelete tempFile

if verbose = 1 then do
   say "Manufacturer:" myManufacturer
   say "Product Name:" myProduct
   say "Version:" myVersion
   say "Serial Number:" mySerial
   say "UUID:" myUUID
   say "BIOS:" myBIOS
   say "BIOS Date:" myBIOSdate
   say "BIOS Revision:" myBIOSrevision
   say "Firmware:" myBIOSfirmware
   say "CPU:" myCPU
end

if myBIOS = "VirtualBox" then do
   if verbose = 1 then do
      say "The system appears to be running in VirtualBox"
   end
   isVirtualBox = 1
end
else do
   if verbose = 1 then do
      say "The system appear to be running on real hardware"
   end
   isVirtualBox = 0
end

return

/* scan various files to get operating system name and version */
getOSname:
osName = ''
if mySysLevel = '4.000' then do
   osName = 'Warp4'
   myOS = 'Warp4'
   myOSVer = vNumber
end
else do
   osName = 'MCP'
   myOS = 'MCP'
   myOSVer = vnumber
end
if stream(letter || ':\sys\install\install.flg', 'c', 'query exists') <> '' then do
   osName = 'ArcaOS'
   osDir = value('osDir',,'os2environment')
   flagfile = osDir || '\install\install.flg'
   osName = linein(flagfile)
   parse var osName os1 osVer oslang
   call stream flagfile, 'c', 'close'
   myOS = 'ArcaOS'
   myOSver = left(osVer, 3)
end
if stream(letter || ':\ecs\ECS_INST.FLG', 'c', 'query exists') <> '' then do
   osName = 'eCS'
   osDir = value('osDir',,'os2environment')
   flagfile = osDir || '\ECS_INST.FLG'
   flagfile = letter || ':\ecs\ECS_INST.FLG'
   osName = linein(flagfile)
   parse var osName os1 osVer oslang osDate
   call stream flagfile, 'c', 'close'
   myOS = 'eCS'
   myOSver = osVer
end
if stream(letter || ':\memboot.bin', 'c', 'query exists') <> '' then osName = 'Recovery'

if verbose = 1 then do
   say myOS myOSver
   say "------"
   say osName
   say ""
end

return

/* OS/2 version
 *
 * Thanks to Bob Eager for fixpak data
 * http://www.tavi.co.uk/os2pages/levels.html
 *
 * Written by Neil Waldhauer
 * November 3, 2004, updated Dec 1, 2024
 */
os2version:
address cmd '@cmd /c ver /r | rxqueue'

do while queued() > 0
   parse pull versionline
   versionline = strip(versionline)
   parse var versionline rv revision
   if rv = 'Revision' then do
      call printversion revision
   end
end

return ver

PrintVersion:

select
   when arg(1) = '8.200' then ver = 'Warp 3 GA'
   when arg(1) = '8.209' then ver = 'Warp 3 FixPak 3 (or Warp Connect GA)'
   when arg(1) = '8.234' then ver = 'Warp 3 FixPak 10'
   when arg(1) = '8.235' then ver = 'Warp 3 FixPak 11'
   when arg(1) = '8.241' then ver = 'Warp 3 FixPak 17'
   when arg(1) = '8.246' then ver = 'Warp 3 FixPak 22'
   when arg(1) = '8.250' then ver = 'Warp 3 FixPak 26'
   when arg(1) = '8.256' then ver = 'Warp 3 FixPak 32'
   when arg(1) = '8.264' then ver = 'Warp 3 FixPak 40'
   when arg(1) = '8.265' then ver = 'Warp 3 FixPak 41 (or 42)'
   when arg(1) = '8.267' then ver = 'Warp 3 FixPak 43'
   when arg(1) = '9.023' then ver = 'Warp 4 GA'
   when arg(1) = '9.025' then ver = 'Warp 4 FixPak 1'
   when arg(1) = '9.027' then ver = 'Warp 4 FixPak 3'
   when arg(1) = '9.028' then ver = 'Warp 4 FixPak 4'
   when arg(1) = '9.029' then ver = 'Warp 4 FixPak 5'
   when arg(1) = '9.030' then ver = 'Warp 4 FixPak 6'
   when arg(1) = '9.031' then ver = 'Warp 4 FixPak 7'
   when arg(1) = '9.032' then ver = 'Warp 4 FixPak 8'
   when arg(1) = '9.033' then ver = 'Warp 4 FixPak 9'
   when arg(1) = '9.034' then ver = 'Warp 4 FixPak 10'
   when arg(1) = '9.036' then ver = 'Warp 4 FixPak 11 (or 12)'
   when arg(1) = '14.039' then ver = 'WSeB GA'
   when arg(1) = '14.040' then ver = 'Warp 4 FixPak 13 (or WSeB FixPak 1)'
   when arg(1) = '14.044' then ver = 'Warp 4 FixPak 14'
   when arg(1) = '14.062' then ver = 'Warp 4 FixPak 15 (or WSeB FixPak 2 or Convenience Pack 1 GA)'
   when arg(1) = '14.072' then ver = 'Convenience Pack FixPak 1'
   when arg(1) = '14.086' then ver = 'Convenience Pack 2 GA'
   when arg(1) = '14.088' then ver = 'Convenience Pack FixPak 2 (or WSeB FixPak 3 or Warp 4 FixPak 16)'
   when arg(1) = '14.093' then ver = 'Convenience Pack FixPak 3'
   when arg(1) = '14.097' then ver = 'Convenience Pack FixPak 4 (or Warp 4 FixPak 17)'
   when arg(1) = '14.103' then ver = 'Convenience Pack FixPak 5'
   when arg(1) = '14.105' then ver = 'Convenience Pack FixPak 6'
   otherwise ver = 'unknown version' arg(1)
end

if verbose = 1 then do
   say arg(1) '--' ver
end

return


/* OS/2 version number from syslevel.os2 file */
OS2sysLevel:

sf = FindBootDrive() || ':\os2\install\syslevel.os2'

if stream(sf, 'c', 'query exists') = '' then do
   return 0
end

leveldata = charin( sf, , chars( sf ) )
call stream sf, 'c', 'close'

parse var leveldata "XR" fplevel "_XR" os2level "_" osdata

zp = pos(d2c(0), osdata)
if zp > 0 then do
   ossyslevelname = left(osdata, zp - 1)
   extraData = substr(osdata, zp + 1)
end

myFixpak = substr(fplevel, 3) + 0
if verbose = 1 then do
   say ossyslevelname 'Fixpak' myFixpak
end

nzp = verify(extraData, d2c(0))
partNumber = substr(extraData, nzp)
zp = pos(d2c(0), partNumber)
if zp > 0 then do
   partNumber = left(partNumber, zp -1)
end
if verbose = 1 then do
   say 'Part Number' partNumber
end

vNumber = c2x(substr(leveldata, 41, 2))
vNumber = left(vNumber, 1) || '.' || substr(vNumber, 2)
if verbose = 1 then do
   say 'version' vNumber 
end

return vNumber


findCDLetter:

alldrive = SysDriveMap()
cdLetter = ''

do while alldrive <> ''
   parse var alldrive thisdrive alldrive
   di = SysDriveInfo(thisdrive)
   if di <> '' then do
      parse var di dletter dfree dtotal dlabel
      if if pos('SUNTAN', dlabel) > 0 then do
         cdLetter = left(dletter, 1)
      end
   end
end

return cdLetter
