Subject: Re: handling NetBSD partitions in the Apple Partition Map [was Re:
To: Darrin B. Jewell <dbj@netbsd.org>
From: Bill Studenmund <wrstuden@netbsd.org>
List: port-macppc
Date: 10/07/2002 14:39:41
On 7 Oct 2002, Darrin B. Jewell wrote:

> The primary issue under discussion is how to properly use
> the Apple Partition Map to hold NetBSD partitions.  Initially,
> the thought was to use a pmPartType of "NetBSD", and
> keep additional information in the pmBootArgs reserved
> area of the partition map entry.  Since we have discovered
> some disadvantages to this idea, we are now considering both
> encoding the fstype name in the pmPartType as well as optionally
> encoding the extra disklabel partition information in the
> pmBootArgs.
>
> Bill Studenmund <wrstuden@netbsd.org> writes:
>
> | On 23 Sep 2002, Darrin B. Jewell wrote:
> | > to hold the disklabel bits that aren't found in the
> | > partition map.  These bits are more generically found in the
> | > "u_int8_t pmBootArgs[128]" field of of a partition map
> | > entry.  I've been talking here in person to the Apple
> | > Developer who is in charge of the MacOS Disk Copy utility
> | > and the author of the MacOS `bless' program.  He has
> | > verified that as long as we use our own entry for the "char
> | > pmPartType[32] field, we can put whatever we want in the
> | > pmBootArgs bits.  However he does recommend that we use a
> | > pmPartType of the form MySoftwareCompany_MyContent and cites
> | > an apple tech pub. (see URL [1] below) Therefore, I would
> | > like to recommend that we use "NetBSD_4.4LFS" for FS_BSDLFS
> | > and even move to "NetBSD_4.2BSD" for FS_BSDFFS.  (If we
> | > really want to support pmPartType of just "NetBSD", I
> | > suggest that we use an on disk NetBSD disklabel within that
> | > partition to describe how the disk data is laid out, but
> | > since that has its own issues, i'm inclined not to go this
> | > route either.)
> |
> | I'd rather not go that route, where we have NetBSD_content. Mainly as we,
> | strictly speaking, have over 20 types of content. Yes, a number of them
> | aren't valid (NetBSD_HFS won't happen :-), and I doubt anyone will put a
> | SVR3 fs on an apple-partitioned disk), but it just seems very clean to not
> | have to translate from text <-> numbers.
>
> We already have to parse the string to interpret it.  This operation
> doesn't have to be particularly inefficient.  The key advantage to
> following the apple guidelines for this is that we can completely
> use apple tools to create a valid netbsd partition entry.  If we
> require pmBootArgs bits to be set for an entry to be valid, then
> only NetBSD tools will be able to create valid partition entries.

I now like this. The concern I had was that we would be about doubling the
number of strings we look at (all the NetBSD variants). But I think it's
the best thing to do.

Oh, one other thing, the code I had (before/currently) would be happy w/o
the extra stuff there. You'd then just get an FFS partition for a "NetBSD"
or "NETBSD/MACPPC" partition.

> | As for the NetBSD disklabel bit, we can't use NetBSD as it's in use as a
> | NetBSD-specific variant partition. i.e. it's being used as the code uses
> | it now. :-|
> While it is true that the disksubr.c does contain current code that uses
> this, there is nothing yet in the tree that creates partition entries
> of this form.  Therefore, I'm not too concerned about breaking
> backward compatiblity for these types of partitions.  I think best
> practice is to remove support for "NetBSD" and avoid using it explicitly
> in the apple partition map for now.  Therefore, 1.6 kernels will
> not accidentally run accross partitions of this type and incorrectly
> handle them.

Note: unless we pull up a change, 1.6 kernels will recognize NetBSD
partitions and look for the info I was hiding there. :-)

> | My personal soap box (:-) is that the way we did NetBSD partitioning
> | inside of mbr partitioning on x86 shouldn't be copied to other
> | partitioning schemes. :-) So I don't like the idea of adding a NetBSD
> | partition on disk.
>
> I also do not think we should perpetuate this method with the
> apple partition map.  However, I would like to point out some details
> of Darwin's IOKit that addtionaly enforce the idea that we should
> not be using pmPartType of "NetBSD".

Sounds good.

> Partition support for Darwin is implemented in its the IOStorageFamily
> classes.  Specifically, different types of partitions are implemented
> as derived classes of IOPartitionScheme.  This class abstracts away
> the specifics of a partition table and maps a string provided by
> darwin to the specific identifiers used in a partition table instance.
> For the Apple Partition map, this string identifier is used directly
> as the pmPartType.  For the fdisk/mbr partition table, this string is
> mapped to the commonly used sysids.  Since the string "NetBSD" maps to
> the mbr/fdisk partition entry of 0xA8, it would be poor to use this
> same name in the apple partition map unless it is interpreted the same
> way as the i386 mbr partition type, with an additional NetBSD
> disklabel on disk.

And since I strongly believe that the mbr partitioning scheme should not
be further propogated, I'll agree to just not use "NetBSD". :-)

> | Yes, it is really needed. Mainly for disaster recovery. Say you have an
> | ffs with a bad superblock. Without the blocksize, frag size, and c/g
> | number, it's hard to find the alternate SBs for recovery. :-| That's why
> | we put it in the disklabel, so that you can get it back for fsck -b.
>
> This is what pencil, paper and all those numbers printed by newfs are
> for!  More seriously though, you are correct, there are good reasons
> to include this information.  I have no problem with optionally
> using the pmBootArgs field for this information, but I want
> to be able to function correctly if the pmBootArgs doesn't contain
> it.

Right. And the code now will function correctly w/o the info too. The one
problem with reusing the magic number from A/UX partitions is that that
part of the disk might have garbage that the code will latch onto (i.e. if
the partition was an A/UX one that was later changed to "NetBSD", bad
or weird things can happen).

> | I thik if we have a signature (and we only use special fields if that
> | signature matches), then I think we're safe for Apple tools.
> Being safe from the Apple tools is not the only requirement.  As I
> mentioned, I want to be able to use apple tools to create NetBSD
> partitions.  We can put a an optional struct partition in the
> pmBootArgs field, with presense possibly indicated by a different
> magic number than the one used by the bzb.  If it does not contradict
> the rest of the apple partition map entry, then its additional values
> can be considered valid, and read into the in-core disklabel.

Yep. And that way we catch if you change the type field with other tools;
the derived partition type and the found partition type (in the struct
partition) will differ.

> | >   Although it is not harmful to add the apple_map field to
> | > the cpu_disklabel, I do think you can track your disklabel
> | > changes without having keep the extra information around.
> | > Specifically, a partition map is constrained as as follows:
> | > "With the exception of the driver descriptor record in block
> | > 0, every block on a disk must belong to a partition." (see
> | > url [2] below) This means that if a disklabel entry changes,
> | > you can easily rediscover how the disklabel entries moved
> | > and the effect this would have on the underlying partition
> | > map.
> |
> | Yes, but I figured that the only place I wanted this code to be used was
> | for updating fs types and frag/block/cpg values. So having a mapping from
> | NetBSD to Apple partition makes life easier, rather than an O(n^2) search
> | (for n partitions, find out where they are in the n on-disk ones), we just
> | have a cached value.
>
> This is premature optimization.  It technically doesn't have to be
> implemented as O(n^2), although it may be easiest to implement as
> such.  Even so, your changes don't remove the existing O(n^2) checks,
> and since disklabels are evaluated relatively infrequently, and the
> number of partitions involved is relatively low, a O(n^2) operation
> here is mostly harmless.

It also serves an additional purpose. It acts as memory. If when reading
the current on-disk APM, we get a differnt NetBSD->APM mapping, the
partitions have changed significantly. I choose to bail at that point. :-)

> | >   You also do several checks for valid conversions.  It
> | > seems more appropriate to do validity checks in
> | > setdisklabel(), especially since it has access to both the
> | > new and the old disklabels without having to read it back in
> | > from the partition map.

Well, the problem is that only this layer knows definitively that we are
playing with an Apple partition map. So having all the checks here seems
best. Especially as the checks don't matter on other paritioning types (I
leave them to whatever they do now). :-)

You're right though that it'd be easier with the old disklabel around. I'm
not sure if I want to do that much of a change to the partition table
interface now though.

> | Note: a few things. 1) there really are three "disklabels" in play.

Actually, there are more than that. There's the old and the new NetBSD
labe, the APM that generated the old NetBSD label, the APM on disk, and
what we want to make the APM on disk. :-)

> | There's the old in-kernel one, there's the new one we're setting, and
> | there's whatever is on the disk. A good bit of this code is trying to
> | catch the case where someone re-writes the on-disk partition and then
> | something tries to re-write the in-core label. I don't want the kernel to
> | ruin the on-disk one since it has in principle less info than the on disk
> | one (there are partitions that exist on disk but not in the disklabel).
>
> True that you don't want to ruin the on-disk one, but it should be safe
> to assume that the in-core one was derived from the on-disk one.
> Therefore, you can diff the in-core one with the new one and apply
> the effects of the diff to the on-disk one.

Well, I don't really feel like writing that code. I'm happy with code that
essentially throws up its hands if there'd be too much change needed. :-)

> | 3) You cite a constraint above for partition maps having non-overlapping
> | partitions. That constraint applies (most certainly) to Apple partition
> | maps, but it does not apply to disklabels. Dangerous, yes, but permitted.
> | So strictly speaking, we have to verify that the new disklabel doesn't
> | have overlapping partitions, if we want to support writing whole
> | disklabels.

[snip]

> | Oh, have you heard anything from Apple about what they are going to do
> | when disks get over 2 TB (2^32 512-byte blocks)? It'll happen soon if it
> | hasn't already, and it'll need a different partition table type.
>
> My understanding is that for the short term, they plan to lie about
> the device blocksize in the drvr_map->sbBlockSize, so that the
> overall block count of the device can fit in 32 bits.

Oh.

Oh oh oh.

That will be, "interesting," as then we will be dealing with say "2k
block" disks that really are 512-byte devices. Hmmm...

Ok, wandering back to the subject at hand (and summarizing a bit I hope).
We want to name the partitions "NetBSD" followed by something. We want
more than just NetBSD, since just NetBSD has implications in Darwin.

There are two things we really want to encode. We want to encode the
partition type (4.2BSD, 4.4LFS, CCD, swap (, boot?), RAID, CGD) and if
it's a macppc root, (mac68k root,) or usr. How do we want to do both?
"_<FS_type>" and "_root"? "_rootppc" and "_root68k"?

Take care,

Bill