I discovered on the 26th that if you attempt to unmount an ISOFS
filesystem while it's busy, the kernel will panic.

This afternoon, I tracked the problem down to "flush" code
in the isofs driver:

*** isofs_node.c.ORIG Wed Feb 28 18:59:56 2018
--- isofs_node.c Wed Feb 28 18:50:12 2018
*** 201,232 ****
--- 201,234 ----

   * stupid fs-specific flush routine
   isoflush(vfsp, vp)
           struct vfs * vfsp;
           struct vnode * vp;
           union iso_ihead *ih;
           struct iso_node *ip, *iq;

         iq = VTOISO(vp);
         for (ih = iso_ihead; ih != &(iso_ihead[INOHSZ]); ih++) {
                 for (ip = ih->ih_chain[0];
                          ip != (struct iso_node *)ih;
                          ip = VTOISO(ip->iso_forw)) {
                          if (ip->iso_fs != vfsp)
                          if (iq != (struct iso_node *) 0 && ip != iq)
                          if (ip->iso_count != 0) {
                                   if (ip->iso_count != 0)
                                            return (EBUSY);
                                   goto loop;
         return (0);

I don't understand why, despite the vnode being "busy," there was
an attempt to force that purge and free of the node. There won't
be any pending write data to flush, since ISOFS mounts are read-only.
I've #ifdef'd out those two lines and unmounting an ISOFS while
the vnode is in use now errors with EBUSY as expected. Mach 2.6
doesn't have umount "force" capability, so it wouldn't be useful
to attempt a rude unmount.

The ISOFS driver code is incomplete, based on comments in the code
itself. This may just be a problem characteristic of this new
ISOFS functionality having just been introduced into 2.6MSD when
it was released by Mt Xinu.

February 18, 2018 UPDATE

A new interesting problem discovered today. I suddenly noticed that
the SMC WD80x3 ethernet driver is not discovering the card's MAC
hardware address correctly. It was only reporting the first three
bytes correctly--the last three were always zeroes.

This was discovered when I was trying to bring up a second Mach386
machine as a testbed for new kernel and other software builds.

I first suspected a hardware problem, and swapped cards. The same
thing was occurring. Worse yet, I checked the main development
machine... and it was occurring there as well.

The problem is only noticed now because trying to use two Mach386
machines on the same network caused a MAC conflict between them.
They both were using the MAC ID of 00:00:c0:00:00:00. tcpdump(1)
verified that the incorrect MAC ID was being used on ethernet

I couldn't be sure that I had actually seen the MAC addresses
correctly determined under Mach386. My recollection was that I
only ever paid attention to the MAC was when utilizing the
SMC EZsetup software and sending out test packets from the DIAGNOSE

So I booted up DRDOS and checked out the DIAGNOSE utility. I saw
the correct MAC id being sent onto the network. This verifies that
the network cards are not at fault.

I turned my attention to the Mach386 kernel. I began booting
older kernels that I've built, presuming that I had made an errant
change. All showed the same MAC problem.

Then I tried the last custom-built kernel from 1993, which I built
from updates from Mt Xinu. This one failed as well.

I then reverted to the latest Mt Xinu floppy distribution kernel.
I must take care when running this kernel, as it has differences
in the disk drivers and disk labeling software. It can be destructive
to try to fsck(8) a large filesystem with it. I avoided letting fsck(8)
get run.

This Mt Xinu kernel probed the MAC address correctly.

OK, back to the kernel sources then. Obviously something happened
to the if_ns8390.c driver code for the SMC 80x3 cards.

Long story short, I found the following code in the driver:

if (((u_char) inb(hdwbase+IFWD_LAR_0) == (u_char) WD_NODE_ADDR_0) &&
         ((u_char) inb(hdwbase+IFWD_LAR_1) == (u_char) WD_NODE_ADDR_1) &&
         ((u_char) inb(hdwbase+IFWD_LAR_2) == (u_char) WD_NODE_ADDR_2)) {
     ns8390info[unit] = dev;
     sp->card = wd8003_card;
     ev->name = wd8003_card;
     sp->nic = hdwbase + OFF_8390;
     /* enable mem access to board */
     sp->board_id = wd80xxget_board_id(dev);

     *(sp->address) = inb(hdwbase+IFWD_LAR_0);
     *(sp->address + 1) = inb(hdwbase+IFWD_LAR_1);
     *(sp->address + 2) = inb(hdwbase+IFWD_LAR_2);
     *(sp->address + 3) = inb(hdwbase+IFWD_LAR_3);
     *(sp->address + 4) = inb(hdwbase+IFWD_LAR_4);
     *(sp->address + 5) = inb(hdwbase+IFWD_LAR_5);
     return TRUE;
} /* checks the address of the board to verify that it is a WD */

And keeping the story short... That call to wd80xxget_board_id(dev) is
where the trouble occurs. Once that function returns, the inb(...) calls
to obtain bytes from the card are returning a value of zero.

I haven't investigated the fault further. But I've worked around the
problem for now.

I've moved that board_id function call to *AFTER* assigning the MAC address bytes
with the inb() functions.

I will spend time at a later date to fully determine the problem and resolution.
It may be an issue of CPU speed/timing; Back in the early 90's, I likely ran
a 486DX2 50 or 100mhz machine for Mach386. Today, I'm running it on a Pentium
III 800mhz and a Celeron 500mhz machines.

February 17, 2018 UPDATE

Thanks to Amazon.com, my Mach386 development system is working again.
After ordering 40 1000uf 6.3v electrolytic capacitors from them at
11:30pm last night, they arrived at 12:00 (noon) today. 12 hours and
30 minutes after ordering, and another two hours replacing all 24
capacitors on the motherboard, and it is working solidly again.

I took my time on the capacitor replacement. I replaced three to four
at a time, and tested the motherboard at each interval. The motherboard
came alive again after the second set, which was a group of capacitors
just along the Slot-1 CPU itself. I continued replacing all the capacitors
in groups ensuring that, had I made any mistakes soldering, it would
be easy to locate and resolve. I did not have to rework any replacements
or otherwise make corrections on the board.

While I was awaiting the board repair, I began trying to understand and
document how to install Mach386 to a disk, or add a new disk drive to an
existing Mach386 system, which is greater than 4GB. There are a number
of issues with large drives and this older UNIX operating system. The
issues exist not only for IDE/ATA drives but the same problems exist for
SCSI drives.

The fundamental problem is that while Mach386 disk drivers will happily
use whatever configuration they're told, they obtain the disk geometry
from a Mach VTOC stored on the drive. To get this VTOC created, one
must use a combination of the utilities fdisk(8), badblocks(8), vtoc(8)
and diskutil(8) to get a drive set-up for Mach to use. The trick lies
in getting a working VTOC written with a geometry different than what
BIOS or the device itself has reported.

The Mach386 kernel drivers are not able to readjust a disk's geometry
dynamically. So there are a number of reboots that must occur. In
particular, immediately after changing the geometry for the fdisk
partition, the VTOC partition and then again after generating the Mach

Mach partitions are very similar to disklabel(8) partitioning and while
reported by disklabel(8), are not the same. The earlier (pre-March 1992)
Mach386 systems did not use VTOC. VTOC was introduced after that time
both in floppy distributions as well as sysload(8)/online updates. Once
VTOCs are employed, the disklabel(8) facility should not be used and
will even cause problems if partitioning is changed via disklabel(8).

I did manage to add an additional ATA 10GB drive today and partition, format
and copy filesystems from a SCSI disk. This was, however, not easy
and very time consuming primarily due to the empirical learning and under-
standing of the process to change geometries to within the 4GB limit.
I plan to continue determining how to best perform this process and
will document it.

I really wish I could find Mach 2.6MSD sources, especially to these
disk utilities.

February 16, 2018 UPDATE

Today, after some heavy searching, I've found sources to a number of
utilities customized by CMU. In particular, I've found the CMU-modified
sources for the version of csh(1) in MACH 2.5. This is important, because
there is at least one bug ("cd ../.." at root will crash csh). I've found
the problem, fixed it, and rebuilt csh. The problem is resolved now.
Additionally, the binary sizes are so close that it gives me confidence that
the found csh source code really is that which was used in Mach 2.5:

root@mod43:/ 5 # ls -l /usr/build/obj/usr/cs/bin/csh/csh /bin/csh
-rwxr-xr-x 1 mtxinu 122904 Jan 27 1991 /bin/csh
-rwxr-xr-x 1 root 122912 Feb 16 16:56 /usr/build/obj/usr/cs/bin/csh/csh
root@mod43:/ 6 # size /usr/build/obj/usr/cs/bin/csh/csh /bin/csh
text data bss dec hex
118752 4128 15692 138572 21d4c /usr/build/obj/usr/cs/bin/csh/csh
118752 4120 15752 138624 21d80 /bin/csh

Work continues with the distribution-generation utility for sysload(8).

LATE update:

Suddenly, after many weeks of working on Mach386 using my lone ISA-based
computer, the system suddenly became unstable and generally wouldn't boot
or even begin the BIOS POST test.

Examination of the motherboard revealed why: Almost every one of the electrolytic
capacitors on the motherboard had suddenly swelled, with many having almost popped
the can off. There was no physical leakage onto the motherboard, however. All of
this literally occurred within a 12-hour period; I specifically examine them periodically.

While I have a spare motherboard and CPU, it only has one ISA slot. I need
at least two ISA slots to accommodate the Adaptec SCSI and the SMC 80x3 ether
boards being used for Mach386.

I've ordered new capacitors from Amazon at a very good price, and they're
expected by tomorrow evening--free next day shipping with my Amazon Prime.