SunOS 4.0.3c SPARC

Aus Knowledgebase
Zur Navigation springen Zur Suche springen

Installing SunOS 4.0.3c on a SPARCstation 1

The SPARCstation 1 was released in 1989 and was the first of a long line of iconic pizza box style workstations. SunOS 4.0.3c was a special hardware support release for this new "sun4c" architecture. It was originally available on QIC tape and floppy disks. The floppy disk version has survived the test of time and disk images are now available from your abandonware repository of choice.

The SS1 needs an Open Boot Prom (OBP) version 1.X. A version 2.X can't boot SunOS 4.0 anymore and require SunOS 4.1.1 or newer. If you have an IPC, you can "setenv version2? false" to enable a 1.X compatibility mode. Unfortunately, this feature is not available on the SS1.

As far as the hardware goes, the SS1 comes with a 20MHz SPARCv7 CPU. I assume that you have loaded it with as much 4MB SIMMs as possible (up to 64MB). Base configuration in '89 was 8MB, which was generally seen as "not enough". In terms of graphics, 4.0.3c will likely support bwtwo, cgthree, and the original double width cgsix. The Field Engineer's Handbook says that you shouldn't run an SS1 without any disks and sbus cards, so I would recommend always having "something" in there, even if you don't intend to use it. This might be an issue if you for example use an empty machine with serial console and a SCSI-to-SD adapter. It originally came with internal 100MB 3.5" disks, which were seen as "not big enough". Larger external disks were common as well.

Sun SPARCstation 1
Sun promo picture 1989
Sun promo picture 1989


fixing the NVRAM

this machine uses an M48T02 NVRAM, so naturally for a 30-year-old machine the battery is most likely empty. You can still buy replacement NVRAMs (these days often of unknown quality if you end up with a part from a Chinese eBay seller) or you can fix the NVRAM if you have the necessary hardware/soldering skills. After that, the NVRAM needs reprogramming:

enter this series of commands at the "ok" prompt:

press enter after these commands:

set-defaults
setenv diag-switch? false
f idprom@ 1 xor f mkp

then at last enter this command. Press enter and it will do "nothing". Then you need to confirm with "control-D", "control-R". If it DOESN'T print a copyright message, it worked.

8 0 20 B2 E9 08 B2E908 mkpl


disks

disks need to have a Sun disklabel. SunOS 4 relies on a format.dat and can technically only label disks it knows, because it doesn't have an auto-detect feature. Solaris however uses the same disklabel and its format utility can autodetect disk geometry and label every disk. I generally recommend booting something like Solaris 2.4 to 2.7 and use it to format and partition the disks. The SunOS 4 installation process can then just keep the existing disklabel.

A full installation of SunOS 4.0.3c will use about 65MB + swap space. SunOS 4 uses the old BSD swap mechanism where it can only use as much memory as it has swap space. The old rule was to have twice as much swap space as the machine has RAM. These days, I would be generous with swap, because sometimes building software will need a huge amount of memory.

SunOS releases < 4.1.1 (with a patch) can only use disks up to 1GB. To make my life easier, I decided to use a ZuluSCSI SCSI-to-SD-card adapter. I recommend creating some disk images of about 1000MB size and use these settings in your zuluscsi.ini:

[SCSI]
Debug = 0
SelectionDelay = 255
PhyMode = 0
Quirks = 0
EnableUnitAttention = 0
EnableSCSI2 = 1 # Enable faster speeds of SCSI2
EnableSelLatch = 0
MapLunsToIDs = 0
MaxSyncSpeed = 10 # Set to 5 or 10 to enable synchronous SCSI mode

[SCSI0]
Vendor = "QUANTUM"
Product = "FIREBALL1000S"
Version = "0700"
Type = 0     # 0: Fixed
SectorsPerTrack = 54
HeadsPerCylinder = 15

[SCSI3]
Vendor = "QUANTUM"
Product = "FIREBALL1000S"
Version = "0700"
Type = 0     # 0: Fixed
SectorsPerTrack = 54
HeadsPerCylinder = 15

[SCSI6]
Product = "Zulu CD-ROM"
Type = 2

Note that the adjustment of Sectors/Heads is necessary to be able to properly format the disk in SunOS. Disk images should be HD0.img, HD3.img, and so on. The cd-rom image should be CD6_512.iso. The will emulate a proper 512-byte/sector cd-rom. ID6 is the default SCSI ID for cd-roms on Suns.

SPARCstations switch up SCSI ids. SCSI ID 3 becomes disk (sd0) and SCSI ID 0 becomes disk3 (sd3). The assumed story behind this is that originally the older Sun3 machines used to boot from SCSI ID 0. Since all disks were external, people wanted to reuse their disks with newer SPARCs. To make the transition easier, Sun decided to switch the new default SCSI ID from 0 to 3. In order to avoid that people would have to learn new commands, they also changed all the SCSI designations. Whatever the actual truth is, it is still confusing to have ID3 show up as sd0. For the purpose of this installation, I assume that you partitioned sd0 with /, swap, and some /var. sd1 will have /usr. Create as many disks as you like, if you want more filesystems.

Filesystem            kbytes    used   avail capacity  Mounted on
/dev/sd0a             251271    2979  223164     1%    /
/dev/sd1g             980035   61254  820777     7%    /usr
/dev/sd3a             980035  535317  346714    61%    /export
/dev/sd0e             477188      54  429415     0%    /var
/dev/sd2a             980035   46733  835298     5%    /usr/local

Note that the SunOS 4.0.3c generic kernel will assume that SCSI ID 4 and ID5 are tape drives. To change that, you would need a custom kernel.

boot from a cd-rom:

boot sd(0,6,2)

boot from a floppy disk:

boot fd()

installing SunOS

SunOS 4.0.3c

I assume you want to install SunOS using the available floppy images and real floppy disks. Descriptions how to extract the installation files and setup netbooting have been provided elsewhere:

http://www.9600bps.org/solaris/sunos403c_diskless.html

https://kb.pocnet.net/wiki/SunOS_4_network_boot_howto

if you have a SPARCstation IPC, you will need a SCSI patch, in order to install 4.0.3c:

https://halfmanhalftaco.com/2017/08/26/SunOS-403c-on-IPC/


So, get your floppy disks ready and be brave! install_disk_A.img and install_disk_B.img are needed to boot the machine. install_disk_C.img and install_disk_D.img are the miniroot. sunos_disk_1.img to sunos_disk_19.img are the SunOS installation sets.

SunOS has a special quirk: It won't properly work with the common terminal setting of 8N1. You need to set the terminal 7E1 or you will only get messed up output after booting the kernel.

Insert the install_disk_A and boot the machine:

boot fd()

it will ask for install_disk_B and drop you into a shell. You could then "format" the disks, but I assume that you have already done to using Solaris. Sun actually provided a README to install SunOS here. I changed the example to properly match "sd0":

1. use "format" to format and/or label the disk as needed 
2. "eject" the munixfs diskette ("B") if not already ejected
       # eject
3. set the variable "disk" to sd0, sd1 or whatever is appropriate
       # disk=sd0
4. run the extract script by sourceing it
       # . /extract
5. follow its instructions
6. when the shell prompts (with "#"), enter:
       # reboot "sd(0,0,1) -sw"

this will extract the miniroot, copy the miniroot to the swap partition and reboot from that partition. If you mess up the SunOS installation later, the miniroot will still be there. You can restart the installation process simply be booting from the swap partition again ("boot sd(0,0,1) -sw").

Once you boot into the miniroot, SunOS MUNIX will again just drop you into a shell. Enter "suninstall" to start the installation process. The installation process is pretty much the same as with later SunOS releases. Make sure you keep the existing disklabels, choose fd0 as the installation media and feed the machine the other 19 floppy disks. The good thing is, should a disk be unreadable at this point, suninstall will just give you an error and offer you the possibility to try that disk again. That way you can just rewrite the image to a new floppy disk, but you won't have to restart the whole installation process. Let it work and have some patience and it will most likely install just fine. Reboot from the disk ("boot disk") and login to SunOS 4.0.3c.


system configuration

some important binaries are in /usr/5bin. Adjust .cshrc:

set path=(/usr/local/bin /usr/ucb /bin /usr/bin /usr/5bin /etc /usr/etc)

SunOS 4.0.3c won't accept a different $HOME directory for root other than /.


/etc/hosts: enter your host names here. SunOS 4 can't use DNS by default. It was assumed that people would use NIS = YP.

build a custom kernel

cd /usr/sys/sun4c/conf
cp GENERIC MYCONFIG
vi MYCONFIG  #  edit as you like. You will probably want more "maxusers". Set "maxusers" to the amount of RAM in MB you have.
config MYCONFIG
cd ../MYCONFIG
make depend && make
mv /vmunix /vmunix.generic
mv vmunix /

then reboot.


add to /etc/rc.local:

# set default route
echo 'setting default route' > /dev/console
route add default 192.168.2.253 1


setup the shell environment:

# add this to .login:
setenv CONFIG_SHELL "/usr/local/bin/bash"
setenv SHELL /usr/local/bin/bash

setenv CPPFLAGS "-I /usr/local/include"
setenv CFLAGS "-O -I/usr/local/include -L/usr/local/lib"
setenv LDFLAGS "-L/usr/local/lib"

stty cs8 -istrip


installing patches

a number of patches were available for SunOS 4.0.3c. Some of them are seriously recommended, if you know what you are doing. I recommend creating a full backup of the disk or disk image before you start. You will need to rebuild the kernel in the end.

there is a problem with /usr/include/machine/setjmp.h. It will be fixed incorrectly by gcc's fixincludes. This file has been slightly changed in SunOS 4.1.3, but it is basically the same. I recommend just replacing (remember to backup) <machine/setjmp.h>:

/*	@(#)setjmp.h 1.5 89/09/08 SMI; from UCB 4.1 83/05/03	*/

#ifndef	__sparc_setjmp_h
#define	__sparc_setjmp_h

/*
 * onsstack,sigmask,sp,pc,npc,psr,g1,o0,wbcnt (sigcontext).
 * All else recovered by under/over(flow) handling.
 */
#define	_JBLEN	9

typedef	int jmp_buf[_JBLEN];

/*
 * One extra word for the "signal mask saved here" flag.
 */
typedef	int sigjmp_buf[_JBLEN+1];

int	setjmp(/* jmp_buf env */);
int	_setjmp(/* jmp_buf env */);
int	sigsetjmp(/* sigjmp_buf env, int savemask */);
void	longjmp(/* jmp_buf env, int val */);
void	_longjmp(/* jmp_buf env, int val */);
void	siglongjmp(/* sigjmp_buf env, int val */);

/*
 * Routines that call setjmp have strange control flow graphs,
 * since a call to a routine that calls resume/longjmp will eventually
 * return at the setjmp site, not the original call site.  This
 * utterly wrecks control flow analysis.
 */
#pragma unknown_control_flow(sigsetjmp, setjmp, _setjmp)

#endif	/* !__sparc_setjmp_h */


/usr/include/sys/termios.h needs a mod:

/* added from SunOS 4.1.3: */
#define IEXTEN  0x00008000

/usr/include/dirent.h and /usr/include/sys/dirent.h are not safe when they are included multiple times. Modify the include files and add something like:

#ifndef __dirent_h
#define __dirent_h
[...rest of dirent.h...]

#endif	/* !_dirent_h */

and...

#ifndef __sys_dirent_h
#define __sys_dirent_h

[...rest of sys/dirent.h...]

#endif	/* !__sys_dirent_h */


/usr/include/time.h and /usr/include/sys/time.h also need a fix:


#ifndef __time_h
#define __time_h

[...]

#endif  /* !__time_h */


#ifndef _sys_time_h
#define _sys_time_h

[...]

#endif /*!_sys_time_h*/


This is what SunOS 4.1.3 does and it works fine... Do not forget any fixed gcc include files if applicable...


building software

general notes:

config.guess can't autodetect the OS. Just give sparc-sun-sunos4.0.3. SunOS cc can't use -O and -g together. GNU autoconf will then generally use -g. I recommend to use optimization instead. You will probably need to fix the Makefiles yourself.


sed-3.0.2:

sed/utils.h:
needs:  #include <sys/types.h>


bash-2.03:

lib/readline/shell.c:
#define NULL 0


flex-2.5.4

m4-1.4

make-3.75

bison-1.28

gcc-2.4.5

gzip-1.2.4a

pdksh-5.2.14

tar-1.11.8


top-3.5.1:

os.h:

uncomment inclusion of stdlib.h, because we don't have that here.

utils.c:

#include <missing_snprintf.h>

gcc-2.4.5 and gcc-2.5.8 also work.

gcc-2.6.3:

configure --enable-languages=c,c++ sparc-sun-sunos4.0.3 && make bootstrap


make-3.79.1:

configure --disable-nls sparc-sun-sunos4.0.3 && make
glob/fnmatch.c:
#define NULL 0
#include <sys/types.h>

glob/fnmatch.c:
#include <sys/types.h>
#define NULL 0

function.c and job.c:
#ifndef remove
#define remove unlink
#endif
remove() should remove both files and directories. unlink() only removes files.


bash-2.04 and bash-2.05b:

won't properly run configure with the SunOS /bin/sh. Use bash.

FAILS: bash > 2.03 wants to use set locale, which doesn't exist here.


gcc-2.7.2.3:

collect2.c:
uncomment include unistd.h

cp/errfn.c:
extern int sprintf (char *, const char *, ...);

../gcc-2.7.2.3/configure --enable-languages=c,c++ sparc-sun-sunos4.0.3

will use cc first. change Makefile to use gcc (CC and OLDCC).

Note: c++ doesn't work. g++ will build, but lilbstdc++ won't.


unzip-5.52

fileio.c:
#include <missing_strerror.h>


libiconv-1.9.2:

srclib/gettext.h:
uncomment the #include <locale.h>

srclib/progreloc.c:
#include <sys/types.h>
before the #include stat.h

srclib/setenv.c:
srclib/unsetenv.c:
#define NULL 0
#include <sys/types.h>


expat-2.0.1:

lib/xmlparse.c:
xmlwf/xmlwf.c:

#include <sys/types.h>
extern void *malloc(size_t);
extern void *realloc(void *, size_t);
extern void free(void *);

xmlwf/xmltchar.h:
#ifndef remove
#define remove unlink
#endif

tests/runtests.c:
#define EXIT_SUCCESS 0
#define EXIT_FAILURE 1

tests/minicheck.c
#include <sys/types.h>


X11R5:

FAILS. Can't even compile imake...


X11R4:

edit config/site.def and config.sun.cf
make sure it has:
#define HasGcc YES

as well as:
#define OSName		  SunOS 4.0.3
#define OSMajorVersion	  4
#define OSMinorVersion	  0

libXt won't build, because one file want to include stdarg.h.
uncomment that.

then just do a "make World".

some include files seem to live in /usr/include/X11/Xaw, but appear to be expected in /usr/include/X11... fix like: cd /usr/include/X11; ln -s Xaw/Form.h ./


gawk-3.0.6:

protos.h:
#include <sys/types.h>

#this usually lives in SunOS 4.1's <sys/stdtypes.h>:
typedef      unsigned short  mode_t;


ncurses-5.9:

test/dots.c:
test/dots_mvcur.c:
#define	STDOUT_FILENO	1	/* Standard output.  */

test/ncurses.c:
#include <missing_strstr.h>

test/railroad.c:
#define	STDOUT_FILENO	1	/* Standard output.  */


ncurses needs some mods in SunOS:

sys/termios.h, dirent.h, and sys/dirent.h. (see above).


texinfo-4.8:

lib/gettext:
uncomment include locale.h

infodoc.c:
#include <missing_strstr.h>

makeinfo/lang.c:
#include <missing_strstr.h>


readline-6.1:

xmalloc.h:
#include <sys/types.h>

history.h:
#include <sys/types.h>


vim-5.8:

os_unix.c:
#define       TCSANOW         0

option.c:
#include <missing_strstr.h>

Note: SunOS 4.0.3 does have termios, but it appears to be incomplete. if you get error related to termios, you can often edit config.h and set #undef HAVE_TERMIOS_H. termio.h will generally work.


byacc-20180609:

defs.h:
#include <sys/types.h>
#define EXIT_SUCCESS 0
#define EXIT_FAILURE 1
#define W_OK         2

typedef      unsigned short  mode_t;
gcc-2.7.2.3 can't understand the ATTRIBUTE_NORETURN. delete that.

main.c
#include <missing_atexit.h>

make sure it installs as byacc.


xpm-3.4k:

use make -f Makefile.noX

edit lib/Makefile.noX and add DEFINES:
-DNEED_STRCASECMP

SunOS 4.0.3 does not have strcasecmp(), even though SunOS 4.1.3 does.

TODO: also needs shared libraries...


m4-1.4.3

./configure sparc-sun-sunos4.0.3 && make


tin-2.6.3snap1:

./configure --with-libiconv-prefix=/usr/local --disable-ipv6 --enable-broken-system-fix --disable-locale --enable-nntp-default-server=news --with-screen=ncurses --enable-nntp-only --with-domain= --with-editor=/usr/local/bin/vim sparc-sun-sunos4.0.3

makecfg.c:
#define EXIT_SUCCESS 0
#define EXIT_FAILURE 1

intl/many files:
delete the inclusion of locale.h

add to pcre/pcre_globals.c:
#include <sys/types.h>
extern void *malloc(size_t);
extern void *realloc(void *, size_t);
extern void free(void *);


bison-1.875:

lib/gettext.h:
delete the include locale.h

argmatch.c:
#define EXIT_SUCCESS 0
#define EXIT_FAILURE 1

lots of files need any one of these:

#define NULL 0
extern void free(void *);
#include <sys/types.h>


textutils-1.22:

pr.c:
#include <missing_strftime.h>


less-418:

charset.h:
missing_strstr.h


gcc-2.8.1:

--enable-languages=c sparc-sun-sunos4.0.3
Note: c++ doesn't work. g++ will build, but lilbstdc++ won't.

cpplib.c:
needs
#include <sys/types.h>
to have time_t.


gcc-2.95.3:

../gcc-2.95.3/configure --enable-languages=c --disable-nls sparc-sun-sunos4.0.3 && make bootstrap

Note: c++ doesn't work. g++ will build, but lilbstdc++ won't.

gcc-2.95.3 needs the fixes for /usr/include/time.h and /usr/include/sys/time.h.

../gcc-2.95.3/libiberty/mkstemps.c
#include <sys/types.h>

../gcc-2.95.3/libiberty/setenv.c
#include <sys/types.h>
#define NULL 0

../gcc-2.95.3/gcc/cp/errfn.c:
extern int sprintf (char *, const char *, ...);


to be continued