enum{ __XYX__CPU_STATE_MAX = CPU_STATE_MAX, __XYX__CPU_STATE_USER = CPU_STATE_USER , __XYX__CPU_STATE_SYSTEM = CPU_STATE_SYSTEM, __XYX__CPU_STATE_IDLE = CPU_STATE_IDLE , __XYX__CPU_STATE_NICE = CPU_STATE_NICE , /* * Capability bits used in the definition of cpu_type. */ __XYX__CPU_ARCH_MASK = CPU_ARCH_MASK , /* mask for architecture bits */ __XYX__CPU_ARCH_ABI64 = CPU_ARCH_ABI64, /* 64 bit ABI */ /* * Machine types known by all. */ __XYX__CPU_TYPE_ANY = CPU_TYPE_ANY, __XYX__CPU_TYPE_VAX = CPU_TYPE_VAX , __XYX__CPU_TYPE_MC680x0 = CPU_TYPE_MC680x0 , __XYX__CPU_TYPE_X86 = CPU_TYPE_X86 , __XYX__CPU_TYPE_I386 = CPU_TYPE_I386 , /* compatibility */ __XYX__CPU_TYPE_X86_64 = CPU_TYPE_X86_64 , /* skip CPU_TYPE_MIPS ((cpu_type_t) 8) */ __XYX__CPU_TYPE_MC98000 = CPU_TYPE_MC98000, __XYX__CPU_TYPE_HPPA = CPU_TYPE_HPPA , __XYX__CPU_TYPE_ARM = CPU_TYPE_ARM , __XYX__CPU_TYPE_MC88000 = CPU_TYPE_MC88000, __XYX__CPU_TYPE_SPARC = CPU_TYPE_SPARC , __XYX__CPU_TYPE_I860 = CPU_TYPE_I860 , /* skip CPU_TYPE_ALPHA ((cpu_type_t) 16) */ __XYX__CPU_TYPE_POWERPC = CPU_TYPE_POWERPC , __XYX__CPU_TYPE_POWERPC64 = CPU_TYPE_POWERPC64 , /* * Machine subtypes (these are defined here, instead of in a machine * dependent directory, so that any program can get all definitions * regardless of where is it compiled). */ /* * Capability bits used in the definition of cpu_subtype. */ __XYX__CPU_SUBTYPE_MASK = CPU_SUBTYPE_MASK , /* mask for feature flags */ __XYX__CPU_SUBTYPE_LIB64 = CPU_SUBTYPE_LIB64, /* 64 bit libraries */ /* * Object files that are hand-crafted to run on any * implementation of an architecture are tagged with * CPU_SUBTYPE_MULTIPLE. This functions essentially the same as * the "ALL" subtype of an architecture except that it allows us * to easily find object files that may need to be modified * whenever a new implementation of an architecture comes out. * * It is the responsibility of the implementor to make sure the * software handles unsupported implementations elegantly. */ __XYX__CPU_SUBTYPE_MULTIPLE = CPU_SUBTYPE_MULTIPLE , __XYX__CPU_SUBTYPE_LITTLE_ENDIAN = CPU_SUBTYPE_LITTLE_ENDIAN , __XYX__CPU_SUBTYPE_BIG_ENDIAN = CPU_SUBTYPE_BIG_ENDIAN , /* * Machine threadtypes. * This is none - not defined - for most machine types/subtypes. */ __XYX__CPU_THREADTYPE_NONE = CPU_THREADTYPE_NONE, /* * VAX subtypes (these do *not* necessary conform to the actual cpu * ID assigned by DEC available via the SID register). */ __XYX__CPU_SUBTYPE_VAX_ALL = CPU_SUBTYPE_VAX_ALL , __XYX__CPU_SUBTYPE_VAX780 = CPU_SUBTYPE_VAX780 , __XYX__CPU_SUBTYPE_VAX785 = CPU_SUBTYPE_VAX785 , __XYX__CPU_SUBTYPE_VAX750 = CPU_SUBTYPE_VAX750 , __XYX__CPU_SUBTYPE_VAX730 = CPU_SUBTYPE_VAX730 , __XYX__CPU_SUBTYPE_UVAXI = CPU_SUBTYPE_UVAXI , __XYX__CPU_SUBTYPE_UVAXII = CPU_SUBTYPE_UVAXII , __XYX__CPU_SUBTYPE_VAX8200 = CPU_SUBTYPE_VAX8200 , __XYX__CPU_SUBTYPE_VAX8500 = CPU_SUBTYPE_VAX8500 , __XYX__CPU_SUBTYPE_VAX8600 = CPU_SUBTYPE_VAX8600 , __XYX__CPU_SUBTYPE_VAX8650 = CPU_SUBTYPE_VAX8650 , __XYX__CPU_SUBTYPE_VAX8800 = CPU_SUBTYPE_VAX8800 , __XYX__CPU_SUBTYPE_UVAXIII = CPU_SUBTYPE_UVAXIII , /* * 680x0 subtypes * * The subtype definitions here are unusual for historical reasons. * NeXT used to consider 68030 code as generic 68000 code. For * backwards compatability: * * CPU_SUBTYPE_MC68030 symbol has been preserved for source code * compatability. * * CPU_SUBTYPE_MC680x0_ALL has been defined to be the same * subtype as CPU_SUBTYPE_MC68030 for binary comatability. * * CPU_SUBTYPE_MC68030_ONLY has been added to allow new object * files to be tagged as containing 68030-specific instructions. */ __XYX__CPU_SUBTYPE_MC680x0_ALL = CPU_SUBTYPE_MC680x0_ALL , __XYX__CPU_SUBTYPE_MC68030 = CPU_SUBTYPE_MC68030 ,/* compat */ __XYX__CPU_SUBTYPE_MC68040 = CPU_SUBTYPE_MC68040 , __XYX__CPU_SUBTYPE_MC68030_ONLY = CPU_SUBTYPE_MC68030_ONLY , /* * I386 subtypes */ __XYX__CPU_SUBTYPE_I386_ALL = CPU_SUBTYPE_I386_ALL , __XYX__CPU_SUBTYPE_386 = CPU_SUBTYPE_386 , __XYX__CPU_SUBTYPE_486 = CPU_SUBTYPE_486 , __XYX__CPU_SUBTYPE_486SX = CPU_SUBTYPE_486SX , __XYX__CPU_SUBTYPE_586 = CPU_SUBTYPE_586 , __XYX__CPU_SUBTYPE_PENT = CPU_SUBTYPE_PENT , __XYX__CPU_SUBTYPE_PENTPRO = CPU_SUBTYPE_PENTPRO , __XYX__CPU_SUBTYPE_PENTII_M3 = CPU_SUBTYPE_PENTII_M3 , __XYX__CPU_SUBTYPE_PENTII_M5 = CPU_SUBTYPE_PENTII_M5 , __XYX__CPU_SUBTYPE_CELERON = CPU_SUBTYPE_CELERON , __XYX__CPU_SUBTYPE_CELERON_MOBILE = CPU_SUBTYPE_CELERON_MOBILE , __XYX__CPU_SUBTYPE_PENTIUM_3 = CPU_SUBTYPE_PENTIUM_3 , __XYX__CPU_SUBTYPE_PENTIUM_3_M = CPU_SUBTYPE_PENTIUM_3_M , __XYX__CPU_SUBTYPE_PENTIUM_3_XEON = CPU_SUBTYPE_PENTIUM_3_XEON , __XYX__CPU_SUBTYPE_PENTIUM_M = CPU_SUBTYPE_PENTIUM_M , __XYX__CPU_SUBTYPE_PENTIUM_4 = CPU_SUBTYPE_PENTIUM_4 , __XYX__CPU_SUBTYPE_PENTIUM_4_M = CPU_SUBTYPE_PENTIUM_4_M , __XYX__CPU_SUBTYPE_ITANIUM = CPU_SUBTYPE_ITANIUM , __XYX__CPU_SUBTYPE_ITANIUM_2 = CPU_SUBTYPE_ITANIUM_2 , __XYX__CPU_SUBTYPE_XEON = CPU_SUBTYPE_XEON , __XYX__CPU_SUBTYPE_XEON_MP = CPU_SUBTYPE_XEON_MP , } #ifdef CPU_SUBTYPE_INTEL_FAMILY uint extractSubtypeIntelFamily(uint x){ return CPU_SUBTYPE_INTEL_FAMILY(x); }
/* * get_arch_from_host() gets the architecture from the host this is running on * and returns zero if the architecture is not known and zero if the * architecture is known. If the parameters family_arch_flag and * specific_arch_flag are not NULL they get fill in with the family * architecture and specific architecure for the host. If the architecture * is unknown and the parameters are not NULL then all fields are set to zero. */ __private_extern__ int get_arch_from_host( struct arch_flag *family_arch_flag, struct arch_flag *specific_arch_flag) { struct host_basic_info host_basic_info; natural_t count; /* cctools-port: unsigned int -> natural_t */ kern_return_t r; mach_port_t my_mach_host_self; if(family_arch_flag != NULL) memset(family_arch_flag, '\0', sizeof(struct arch_flag)); if(specific_arch_flag != NULL) memset(specific_arch_flag, '\0', sizeof(struct arch_flag)); count = HOST_BASIC_INFO_COUNT; my_mach_host_self = mach_host_self(); if((r = host_info(my_mach_host_self, HOST_BASIC_INFO, (host_info_t)(&host_basic_info), &count)) != KERN_SUCCESS){ mach_port_deallocate(mach_task_self(), my_mach_host_self); return(0); } mach_port_deallocate(mach_task_self(), my_mach_host_self); if(family_arch_flag != NULL){ family_arch_flag->cputype = host_basic_info.cpu_type; } if(specific_arch_flag != NULL){ specific_arch_flag->cputype = host_basic_info.cpu_type; specific_arch_flag->cpusubtype = host_basic_info.cpu_subtype; } switch(host_basic_info.cpu_type){ case CPU_TYPE_MC680x0: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_MC680x0_ALL: case CPU_SUBTYPE_MC68030_ONLY: if(family_arch_flag != NULL){ family_arch_flag->name = "m68k"; family_arch_flag->cpusubtype = CPU_SUBTYPE_MC680x0_ALL; } if(specific_arch_flag != NULL){ specific_arch_flag->name = "m68030"; /* * There is a "bug" in the kernel for compatiblity that on * an 030 machine host_info() returns cpusubtype * CPU_SUBTYPE_MC680x0_ALL and not CPU_SUBTYPE_MC68030_ONLY. */ specific_arch_flag->cpusubtype = CPU_SUBTYPE_MC68030_ONLY; } return(1); case CPU_SUBTYPE_MC68040: if(family_arch_flag != NULL){ family_arch_flag->name = "m68k"; family_arch_flag->cpusubtype = CPU_SUBTYPE_MC680x0_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "m68040"; return(1); } break; case CPU_TYPE_POWERPC: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_POWERPC_ALL: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc"; return(1); case CPU_SUBTYPE_POWERPC_601: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc601"; return(1); case CPU_SUBTYPE_POWERPC_603: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc603"; return(1); case CPU_SUBTYPE_POWERPC_603e: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc603e"; return(1); case CPU_SUBTYPE_POWERPC_603ev: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc603ev"; return(1); case CPU_SUBTYPE_POWERPC_604: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc604"; return(1); case CPU_SUBTYPE_POWERPC_604e: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc604e"; return(1); case CPU_SUBTYPE_POWERPC_750: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc750"; return(1); case CPU_SUBTYPE_POWERPC_7400: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc7400"; return(1); case CPU_SUBTYPE_POWERPC_7450: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc7450"; return(1); case CPU_SUBTYPE_POWERPC_970: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "ppc970"; return(1); default: if(family_arch_flag != NULL){ family_arch_flag->name = "ppc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_POWERPC_ALL; } if(specific_arch_flag != NULL){ specific_arch_flag->name = savestr("PowerPC cpusubtype 1234567890"); if(specific_arch_flag->name != NULL) sprintf(specific_arch_flag->name, "PowerPC cpusubtype %u", host_basic_info.cpu_subtype); } return(1); } break; case CPU_TYPE_VEO: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_VEO_1: if(family_arch_flag != NULL){ family_arch_flag->name = "veo"; family_arch_flag->cpusubtype = CPU_SUBTYPE_VEO_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "veo1"; return(1); case CPU_SUBTYPE_VEO_2: if(family_arch_flag != NULL){ family_arch_flag->name = "veo"; family_arch_flag->cpusubtype = CPU_SUBTYPE_VEO_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "veo2"; return(1); case CPU_SUBTYPE_VEO_3: if(family_arch_flag != NULL){ family_arch_flag->name = "veo"; family_arch_flag->cpusubtype = CPU_SUBTYPE_VEO_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "veo3"; return(1); case CPU_SUBTYPE_VEO_4: if(family_arch_flag != NULL){ family_arch_flag->name = "veo"; family_arch_flag->cpusubtype = CPU_SUBTYPE_VEO_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "veo4"; return(1); default: if(family_arch_flag != NULL){ family_arch_flag->name = "veo"; family_arch_flag->cpusubtype = CPU_SUBTYPE_VEO_ALL; } if(specific_arch_flag != NULL){ specific_arch_flag->name = savestr("VEO cpusubtype 1234567890"); sprintf(specific_arch_flag->name, "VEO cpusubtype %u", host_basic_info.cpu_subtype); } return(1); } break; case CPU_TYPE_MC88000: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_MC88000_ALL: case CPU_SUBTYPE_MC88110: if(family_arch_flag != NULL){ family_arch_flag->name = "m88k"; family_arch_flag->cpusubtype = CPU_SUBTYPE_MC88000_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "m88k"; return(1); } break; case CPU_TYPE_I386: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_I386_ALL: /* case CPU_SUBTYPE_386: same value as above */ if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "i386"; return(1); case CPU_SUBTYPE_486: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "i486"; return(1); case CPU_SUBTYPE_486SX: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "i486SX"; return(1); case CPU_SUBTYPE_PENT: /* same as CPU_SUBTYPE_586 */ if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "pentium"; return(1); case CPU_SUBTYPE_PENTPRO: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "pentpro"; return(1); case CPU_SUBTYPE_PENTII_M3: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "pentIIm3"; return(1); case CPU_SUBTYPE_PENTII_M5: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "pentIIm5"; return(1); case CPU_SUBTYPE_PENTIUM_4: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "pentium4"; return(1); default: if(family_arch_flag != NULL){ family_arch_flag->name = "i386"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I386_ALL; } if(specific_arch_flag != NULL){ specific_arch_flag->name = savestr("Intel family 12 model 12345678"); if(specific_arch_flag->name != NULL) sprintf(specific_arch_flag->name, "Intel family %u model %u", CPU_SUBTYPE_INTEL_FAMILY(host_basic_info.cpu_subtype), CPU_SUBTYPE_INTEL_MODEL(host_basic_info.cpu_subtype)); } return(1); } break; case CPU_TYPE_I860: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_I860_ALL: case CPU_SUBTYPE_I860_860: if(family_arch_flag != NULL){ family_arch_flag->name = "i860"; family_arch_flag->cpusubtype = CPU_SUBTYPE_I860_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "i860"; return(1); } break; case CPU_TYPE_HPPA: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_HPPA_ALL: if(family_arch_flag != NULL){ family_arch_flag->name = "hppa"; family_arch_flag->cpusubtype = CPU_SUBTYPE_HPPA_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "hppa"; return(1); case CPU_SUBTYPE_HPPA_7100LC: if(family_arch_flag != NULL){ family_arch_flag->name = "hppa"; family_arch_flag->cpusubtype = CPU_SUBTYPE_HPPA_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "hppa7100LC"; return(1); } break; case CPU_TYPE_SPARC: switch(host_basic_info.cpu_subtype){ case /*CPU_SUBTYPE_SPARC_ALL*/0: if(family_arch_flag != NULL){ family_arch_flag->name = "sparc"; family_arch_flag->cpusubtype = CPU_SUBTYPE_SPARC_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "sparc"; return(1); } break; case CPU_TYPE_ARM: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_ARM_ALL: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "arm"; return(1); case CPU_SUBTYPE_ARM_V4T: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv4t"; return(1); case CPU_SUBTYPE_ARM_V5TEJ: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv5"; return(1); case CPU_SUBTYPE_ARM_XSCALE: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "xscale"; return(1); case CPU_SUBTYPE_ARM_V6: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv6"; return(1); case CPU_SUBTYPE_ARM_V6M: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv6m"; return(1); case CPU_SUBTYPE_ARM_V7: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7"; return(1); case CPU_SUBTYPE_ARM_V7F: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7f"; return(1); case CPU_SUBTYPE_ARM_V7S: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7s"; return(1); case CPU_SUBTYPE_ARM_V7K: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7k"; return(1); case CPU_SUBTYPE_ARM_V7M: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7m"; return(1); case CPU_SUBTYPE_ARM_V7EM: if(family_arch_flag != NULL){ family_arch_flag->name = "arm"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "armv7em"; return(1); } break; case CPU_TYPE_ARM64: switch(host_basic_info.cpu_subtype){ case CPU_SUBTYPE_ARM64_ALL: if(family_arch_flag != NULL){ family_arch_flag->name = "arm64"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM64_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "arm64"; return(1); case CPU_SUBTYPE_ARM64_V8: if(family_arch_flag != NULL){ family_arch_flag->name = "arm64"; family_arch_flag->cpusubtype = CPU_SUBTYPE_ARM64_ALL; } if(specific_arch_flag != NULL) specific_arch_flag->name = "arm64v8"; return(1); } break; } return(0); }
/* * NXFindBestFatArch() is passed a cputype and cpusubtype and a set of * fat_arch structs and selects the best one that matches (if any) and returns * a pointer to that fat_arch struct (or NULL). The fat_arch structs must be * in the host byte order and correct such that the fat_archs really points to * enough memory for nfat_arch structs. It is possible that this routine could * fail if new cputypes or cpusubtypes are added and an old version of this * routine is used. But if there is an exact match between the cputype and * cpusubtype and one of the fat_arch structs this routine will always succeed. */ struct fat_arch * NXFindBestFatArch( cpu_type_t cputype, cpu_subtype_t cpusubtype, struct fat_arch *fat_archs, uint32_t nfat_archs) { uint32_t i; int32_t lowest_family, lowest_model, lowest_index; /* * Look for the first exact match. */ for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype == cputype && (fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == (cpusubtype & ~CPU_SUBTYPE_MASK)) return(fat_archs + i); } /* * An exact match was not found so find the next best match which is * cputype dependent. */ switch(cputype){ case CPU_TYPE_I386: switch(cpusubtype & ~CPU_SUBTYPE_MASK){ default: /* * Intel cpusubtypes after the pentium (same as 586) are handled * such that they require an exact match or they can use the * pentium. If that is not found call into the loop for the * earilier subtypes. */ for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_PENT) return(fat_archs + i); } case CPU_SUBTYPE_PENT: case CPU_SUBTYPE_486SX: /* * Since an exact match as not found look for the i486 else * break into the loop to look for the i386_ALL. */ for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_486) return(fat_archs + i); } break; case CPU_SUBTYPE_I386_ALL: /* case CPU_SUBTYPE_I386: same as above */ case CPU_SUBTYPE_486: break; } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_I386_ALL) return(fat_archs + i); } /* * A match failed, promote as little as possible. */ for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_486) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_486SX) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_586) return(fat_archs + i); } /* * Now look for the lowest family and in that the lowest model. */ lowest_family = CPU_SUBTYPE_INTEL_FAMILY_MAX + 1; for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if(CPU_SUBTYPE_INTEL_FAMILY(fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) < lowest_family) lowest_family = CPU_SUBTYPE_INTEL_FAMILY( fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK); } /* if no intel cputypes found return NULL */ if(lowest_family == CPU_SUBTYPE_INTEL_FAMILY_MAX + 1) return(NULL); lowest_model = INT_MAX; lowest_index = -1; for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if(CPU_SUBTYPE_INTEL_FAMILY(fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == lowest_family){ if(CPU_SUBTYPE_INTEL_MODEL(fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) < lowest_model){ lowest_model = CPU_SUBTYPE_INTEL_MODEL( fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK); lowest_index = i; } } } return(fat_archs + lowest_index); case CPU_TYPE_X86_64: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_X86_64_ALL) return(fat_archs + i); } break; case CPU_TYPE_MC680x0: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_MC680x0_ALL) return(fat_archs + i); } /* * Try to promote if starting from CPU_SUBTYPE_MC680x0_ALL and * favor the CPU_SUBTYPE_MC68040 over the CPU_SUBTYPE_MC68030_ONLY. */ if((cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_MC680x0_ALL){ for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_MC68040) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_MC68030_ONLY) return(fat_archs + i); } } break; case CPU_TYPE_POWERPC: /* * An exact match as not found. So for all the PowerPC subtypes * pick the subtype from the following order starting from a subtype * that will work (contains 64-bit instructions or altivec if * needed): * 970, 7450, 7400, 750, 604e, 604, 603ev, 603e, 603, ALL * Note the 601 is NOT in the list above. It is only picked via * an exact match. For an unknown subtype pick only the ALL type if * it exists. */ switch(cpusubtype & ~CPU_SUBTYPE_MASK){ case CPU_SUBTYPE_POWERPC_ALL: /* * The CPU_SUBTYPE_POWERPC_ALL is only used by the development * environment tools when building a generic ALL type binary. * In the case of a non-exact match we pick the most current * processor. */ case CPU_SUBTYPE_POWERPC_970: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_970) return(fat_archs + i); } case CPU_SUBTYPE_POWERPC_7450: case CPU_SUBTYPE_POWERPC_7400: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_7450) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_7400) return(fat_archs + i); } case CPU_SUBTYPE_POWERPC_750: case CPU_SUBTYPE_POWERPC_604e: case CPU_SUBTYPE_POWERPC_604: case CPU_SUBTYPE_POWERPC_603ev: case CPU_SUBTYPE_POWERPC_603e: case CPU_SUBTYPE_POWERPC_603: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_750) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_604e) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_604) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if((fat_archs[i].cputype & ~CPU_SUBTYPE_MASK) != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_603ev) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_603e) return(fat_archs + i); } for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_603) return(fat_archs + i); } default: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_ALL) return(fat_archs + i); } } break; case CPU_TYPE_POWERPC64: /* * An exact match as not found. So for all the PowerPC64 subtypes * pick the subtype from the following order starting from a subtype * that will work (contains 64-bit instructions or altivec if * needed): * 970 (currently only the one 64-bit subtype) * For an unknown subtype pick only the ALL type if it exists. */ switch(cpusubtype & ~CPU_SUBTYPE_MASK){ case CPU_SUBTYPE_POWERPC_ALL: /* * The CPU_SUBTYPE_POWERPC_ALL is only used by the development * environment tools when building a generic ALL type binary. * In the case of a non-exact match we pick the most current * processor. */ case CPU_SUBTYPE_POWERPC_970: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_970) return(fat_archs + i); } default: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_POWERPC_ALL) return(fat_archs + i); } } break; case CPU_TYPE_MC88000: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_MC88000_ALL) return(fat_archs + i); } break; case CPU_TYPE_I860: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_I860_ALL) return(fat_archs + i); } break; case CPU_TYPE_HPPA: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_HPPA_ALL) return(fat_archs + i); } break; case CPU_TYPE_SPARC: for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if((fat_archs[i].cpusubtype & ~CPU_SUBTYPE_MASK) == CPU_SUBTYPE_SPARC_ALL) return(fat_archs + i); } break; case CPU_TYPE_ARM: { /* * ARM is straightforward, since each architecture is backward * compatible with previous architectures. So, we just take the * highest that is less than our target. */ int fat_match_found = 0; uint32_t best_fat_arch = 0; for(i = 0; i < nfat_archs; i++){ if(fat_archs[i].cputype != cputype) continue; if(fat_archs[i].cpusubtype > cpusubtype) continue; if(!fat_match_found){ fat_match_found = 1; best_fat_arch = i; continue; } if(fat_archs[i].cpusubtype > fat_archs[best_fat_arch].cpusubtype) best_fat_arch = i; } if(fat_match_found) return fat_archs + best_fat_arch; } break; default: return(NULL); } return(NULL); }