1 /* 2 * Copyright (c) 2019 Conrad Meyer <cem@FreeBSD.org>. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 14 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 16 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 17 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 18 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 19 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 20 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 21 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 22 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 23 * SUCH DAMAGE. 24 */ 25 26 #include <sys/cdefs.h> 27 __FBSDID("$FreeBSD$"); 28 29 #include <assert.h> 30 #include <err.h> 31 #include <errno.h> 32 #include <stdbool.h> 33 #include <stdint.h> 34 #include <stdio.h> 35 #include <stdlib.h> 36 #include <string.h> 37 38 #include "fstyp.h" 39 40 /* 41 * This really detects the container format, which might be best supported by 42 * geom_part or a special GEOM class. 43 * 44 * https://developer.apple.com/support/downloads/Apple-File-System-Reference.pdf 45 */ 46 47 #define NX_CKSUM_SZ 8 48 49 typedef uint64_t nx_oid_t; 50 51 typedef uint64_t nx_xid_t; 52 53 struct nx_obj { 54 uint8_t o_cksum[NX_CKSUM_SZ]; /* Fletcher 64 */ 55 nx_oid_t o_oid; 56 nx_xid_t o_xid; 57 uint32_t o_type; 58 uint32_t o_subtype; 59 }; 60 61 /* nx_obj::o_oid */ 62 #define OID_NX_SUPERBLOCK 1 63 64 /* nx_obj::o_type: */ 65 #define OBJECT_TYPE_MASK 0x0000ffff 66 #define OBJECT_TYPE_NX_SUPERBLOCK 0x00000001 67 #define OBJECT_TYPE_FLAGS_MASK 0xffff0000 68 #define OBJ_STORAGETYPE_MASK 0xc0000000 69 #define OBJECT_TYPE_FLAGS_DEFINED_MASK 0xf8000000 70 #define OBJ_STORAGE_VIRTUAL 0x00000000 71 #define OBJ_STORAGE_EPHEMERAL 0x80000000 72 #define OBJ_STORAGE_PHYSICAL 0x40000000 73 #define OBJ_NOHEADER 0x20000000 74 #define OBJ_ENCRYPTED 0x10000000 75 #define OBJ_NONPERSISTENT 0x08000000 76 77 struct nx_superblock { 78 struct nx_obj nx_o; 79 char nx_magic[4]; 80 /* ... other stuff that doesn't matter */ 81 }; 82 83 int 84 fstyp_apfs(FILE *fp, char *label, size_t size) 85 { 86 struct nx_superblock *csb; 87 int retval; 88 89 retval = 1; 90 csb = read_buf(fp, 0, sizeof(*csb)); 91 if (csb == NULL) 92 goto fail; 93 94 /* Ideally, checksum the SB here. */ 95 if (strncmp(csb->nx_magic, "NXSB", 4) != 0 || 96 csb->nx_o.o_oid != OID_NX_SUPERBLOCK || 97 (csb->nx_o.o_type & OBJECT_TYPE_MASK) != OBJECT_TYPE_NX_SUPERBLOCK) 98 goto fail; 99 100 retval = 0; 101 102 /* No label support yet. */ 103 104 fail: 105 free(csb); 106 return (retval); 107 } 108