How to get device make and model on iOS?
Asked Answered
C

23

272

I was wondering if it's possible to determine what kind of iPhone (for example) the currentdevice is? I know it's possible to get the model through
NSString *deviceType = [[UIDevice currentDevice] model];
which will just return whether I have an "iPhone" or an "iPod", BUT I was wondering if it's possible to detect/know if I have an iPhone 3GS vs. and iPhone 4 vs. an iPhone 4S (in actuality, all I really want to do is determine if I have a 3G or not, because I'm doing fairly graphics intensive stuff).

So yeah, let me know, thank you!

Characterize answered 25/6, 2012 at 21:19 Comment(4)
this answer might help: https://mcmap.net/q/44906/-how-to-tell-if-ipad-is-black-or-white-via-code-duplicateBeckybecloud
"(in actuality, all I really want to do is determine if I have a 3G or not, because I'm doing fairly graphics intensive stuff)." - In your case, Apple wisely recommends that you check against the availability of the features you're after, instead of checking the actual device model and making a judgement (for which you would need a table of some sort). The recommended approach is simpler and future-proof.Isbell
This question is very old now and the iPhone 3G is virtually non-existent, but in this case you should have checked the availability of the OpenGL ES 2.0 API by creating a renderer and seeing if it succeeds :-),Isbell
The mode reliable way: https://mcmap.net/q/44868/-how-to-determine-the-current-iphone-device-modelShrift
H
594

EITHER try this library: http://github.com/erica/uidevice-extension/ (by Erica Sadun). (The library is 7-8 years old, and hence is obsolete)

(Sample Code):

    [[UIDevice currentDevice] platformType]   // ex: UIDevice4GiPhone
    [[UIDevice currentDevice] platformString] // ex: @"iPhone 4G"

OR You can use this method:

You can get the device model number using uname from sys/utsname.h. For example:

Objective-C

    #import <sys/utsname.h> // import it in your header or implementation file.

    NSString* deviceName()
    {
        struct utsname systemInfo;
        uname(&systemInfo);
    
        return [NSString stringWithCString:systemInfo.machine
                                  encoding:NSUTF8StringEncoding];
    }

Swift 3

    extension UIDevice {
        var modelName: String {
            var systemInfo = utsname()
            uname(&systemInfo)
            let machineMirror = Mirror(reflecting: systemInfo.machine)
            let identifier = machineMirror.children.reduce("") { identifier, element in
                guard let value = element.value as? Int8, value != 0 else { return identifier }
                return identifier + String(UnicodeScalar(UInt8(value)))
            }
            return identifier
        }
    }

    print(UIDevice.current.modelName)

The result should be:

// Output on a simulator
@"i386"      on 32-bit Simulator
@"x86_64"    on 64-bit Simulator

// Output on an iPhone
@"iPhone1,1" on iPhone
@"iPhone1,2" on iPhone 3G
@"iPhone2,1" on iPhone 3GS
@"iPhone3,1" on iPhone 4 (GSM)
@"iPhone3,2" on iPhone 4 (GSM Rev A)
@"iPhone3,3" on iPhone 4 (CDMA/Verizon/Sprint)
@"iPhone4,1" on iPhone 4S
@"iPhone5,1" on iPhone 5 (model A1428, AT&T/Canada)
@"iPhone5,2" on iPhone 5 (model A1429, everything else)
@"iPhone5,3" on iPhone 5c (model A1456, A1532 | GSM)
@"iPhone5,4" on iPhone 5c (model A1507, A1516, A1526 (China), A1529 | Global)
@"iPhone6,1" on iPhone 5s (model A1433, A1533 | GSM)
@"iPhone6,2" on iPhone 5s (model A1457, A1518, A1528 (China), A1530 | Global)
@"iPhone7,1" on iPhone 6 Plus
@"iPhone7,2" on iPhone 6
@"iPhone8,1" on iPhone 6S
@"iPhone8,2" on iPhone 6S Plus
@"iPhone8,4" on iPhone SE
@"iPhone9,1" on iPhone 7 (CDMA)
@"iPhone9,3" on iPhone 7 (GSM)
@"iPhone9,2" on iPhone 7 Plus (CDMA)
@"iPhone9,4" on iPhone 7 Plus (GSM)
@"iPhone10,1" on iPhone 8 (CDMA)
@"iPhone10,4" on iPhone 8 (GSM)
@"iPhone10,2" on iPhone 8 Plus (CDMA)
@"iPhone10,5" on iPhone 8 Plus (GSM)
@"iPhone10,3" on iPhone X (CDMA)
@"iPhone10,6" on iPhone X (GSM)
@"iPhone11,2" on iPhone XS
@"iPhone11,4" on iPhone XS Max
@"iPhone11,6" on iPhone XS Max China
@"iPhone11,8" on iPhone XR
@"iPhone12,1" on iPhone 11
@"iPhone12,3" on iPhone 11 Pro
@"iPhone12,5" on iPhone 11 Pro Max
@"iPhone12,8" on iPhone SE (2nd Gen)
@"iPhone13,1" on iPhone 12 Mini
@"iPhone13,2" on iPhone 12
@"iPhone13,3" on iPhone 12 Pro
@"iPhone13,4" on iPhone 12 Pro Max

//iPad 1
@"iPad1,1" on iPad - Wifi (model A1219)
@"iPad1,2" on iPad - Wifi + Cellular (model A1337)

//iPad 2
@"iPad2,1" - Wifi (model A1395)
@"iPad2,2" - GSM (model A1396)
@"iPad2,3" - 3G (model A1397)
@"iPad2,4" - Wifi (model A1395)

// iPad Mini
@"iPad2,5" - Wifi (model A1432)
@"iPad2,6" - Wifi + Cellular (model  A1454)
@"iPad2,7" - Wifi + Cellular (model  A1455)

//iPad 3
@"iPad3,1" - Wifi (model A1416)
@"iPad3,2" - Wifi + Cellular (model  A1403)
@"iPad3,3" - Wifi + Cellular (model  A1430)

//iPad 4
@"iPad3,4" - Wifi (model A1458)
@"iPad3,5" - Wifi + Cellular (model  A1459)
@"iPad3,6" - Wifi + Cellular (model  A1460)

//iPad AIR
@"iPad4,1" - Wifi (model A1474)
@"iPad4,2" - Wifi + Cellular (model A1475)
@"iPad4,3" - Wifi + Cellular (model A1476)

// iPad Mini 2
@"iPad4,4" - Wifi (model A1489)
@"iPad4,5" - Wifi + Cellular (model A1490)
@"iPad4,6" - Wifi + Cellular (model A1491)

// iPad Mini 3
@"iPad4,7" - Wifi (model A1599)
@"iPad4,8" - Wifi + Cellular (model A1600)
@"iPad4,9" - Wifi + Cellular (model A1601)

// iPad Mini 4
@"iPad5,1" - Wifi (model A1538)
@"iPad5,2" - Wifi + Cellular (model A1550)

//iPad AIR 2
@"iPad5,3" - Wifi (model A1566)
@"iPad5,4" - Wifi + Cellular (model A1567)

// iPad PRO 9.7"
@"iPad6,3" - Wifi (model A1673)
@"iPad6,4" - Wifi + Cellular (model A1674)
@"iPad6,4" - Wifi + Cellular (model A1675)

//iPad PRO 12.9"
@"iPad6,7" - Wifi (model A1584)
@"iPad6,8" - Wifi + Cellular (model A1652)

//iPad (5th generation)
@"iPad6,11" - Wifi (model A1822)
@"iPad6,12" - Wifi + Cellular (model A1823)
         
//iPad PRO 12.9" (2nd Gen)
@"iPad7,1" - Wifi (model A1670)
@"iPad7,2" - Wifi + Cellular (model A1671)
@"iPad7,2" - Wifi + Cellular (model A1821)
         
//iPad PRO 10.5"
@"iPad7,3" - Wifi (model A1701)
@"iPad7,4" - Wifi + Cellular (model A1709)

// iPad (6th Gen)
@"iPad7,5" - WiFi
@"iPad7,6" - WiFi + Cellular

// iPad (7th Gen)
@"iPad7,11" - WiFi
@"iPad7,12" - WiFi + Cellular

//iPad PRO 11"
@"iPad8,1" - WiFi
@"iPad8,2" - 1TB, WiFi
@"iPad8,3" - WiFi + Cellular
@"iPad8,4" - 1TB, WiFi + Cellular

//iPad PRO 12.9" (3rd Gen)
@"iPad8,5" - WiFi
@"iPad8,6" - 1TB, WiFi
@"iPad8,7" - WiFi + Cellular
@"iPad8,8" - 1TB, WiFi + Cellular

//iPad PRO 11" (2nd Gen)
@"iPad8,9" - WiFi
@"iPad8,10" - 1TB, WiFi

//iPad PRO 12.9" (4th Gen)
@"iPad8,11" - (WiFi)
@"iPad8,12" - (WiFi+Cellular)

// iPad mini 5th Gen
@"iPad11,1" - WiFi
@"iPad11,2" - Wifi  + Cellular

// iPad Air 3rd Gen
@"iPad11,3" - Wifi 
@"iPad11,4" - Wifi  + Cellular

// iPad (8th Gen)
@"iPad11,6" - iPad 8th Gen (WiFi)
@"iPad11,7" - iPad 8th Gen (WiFi+Cellular)

// iPad Air 4th Gen
@"iPad13,1" - iPad air 4th Gen (WiFi)
@"iPad13,2" - iPad air 4th Gen (WiFi+Cellular)

//iPod Touch
@"iPod1,1"   on iPod Touch
@"iPod2,1"   on iPod Touch Second Generation
@"iPod3,1"   on iPod Touch Third Generation
@"iPod4,1"   on iPod Touch Fourth Generation
@"iPod5,1"   on iPod Touch 5th Generation
@"iPod7,1"   on iPod Touch 6th Generation
@"iPod9,1"   on iPod Touch 7th Generation

// Apple Watch
@"Watch1,1" on Apple Watch 38mm case
@"Watch1,2" on Apple Watch 38mm case
@"Watch2,6" on Apple Watch Series 1 38mm case
@"Watch2,7" on Apple Watch Series 1 42mm case
@"Watch2,3" on Apple Watch Series 2 38mm case
@"Watch2,4" on Apple Watch Series 2 42mm case
@"Watch3,1" on Apple Watch Series 3 38mm case (GPS+Cellular)
@"Watch3,2" on Apple Watch Series 3 42mm case (GPS+Cellular)
@"Watch3,3" on Apple Watch Series 3 38mm case (GPS)
@"Watch3,4" on Apple Watch Series 3 42mm case (GPS)
@"Watch4,1" on Apple Watch Series 4 40mm case (GPS)
@"Watch4,2" on Apple Watch Series 4 44mm case (GPS)
@"Watch4,3" on Apple Watch Series 4 40mm case (GPS+Cellular)
@"Watch4,4" on Apple Watch Series 4 44mm case (GPS+Cellular)
@"Watch5,1" on Apple Watch Series 5 40mm case (GPS)
@"Watch5,2" on Apple Watch Series 5 44mm case (GPS)
@"Watch5,3" on Apple Watch Series 5 40mm case (GPS+Cellular)
@"Watch5,4" on Apple Watch Series 5 44mm case (GPS+Cellular)
@"Watch5,9" on Apple Watch SE 40mm case (GPS)
@"Watch5,10" on Apple Watch SE 44mm case (GPS)
@"Watch5,11" on Apple Watch SE 40mm case (GPS+Cellular)
@"Watch5,12" on Apple Watch SE 44mm case (GPS+Cellular)
@"Watch6,1" on Apple Watch Series 6 40mm case (GPS)
@"Watch6,2" on Apple Watch Series 6 44mm case (GPS)
@"Watch6,3" on Apple Watch Series 6 40mm case (GPS+Cellular)
@"Watch6,4" on Apple Watch Series 6 44mm case (GPS+Cellular)
Hoang answered 25/6, 2012 at 21:41 Comment(23)
Does this put the appstore approval of my app in risk?Snider
How do I call the machineName method?Aguste
@Aguste Just do something like this: NSLog(@"Device: %@", machineName());Hoang
Will this get my app approved on the app store?Lapse
@Lapse Never had any issue with application approval. :)Hoang
It's time to update the list for new iPhone 8 and X, someone installed the Xcode 9 may help.Eldoria
@Aguste NSLog(@" Device: %@", deviceName());Peavy
@Eldoria Added device ids for iPhone 8 & X. :)Hoang
Any way we can identify iPhone X in the simulator? It appears that it ony responds with "Simulator"Booby
I think the iPad Pro models may be wrong in this list. They seem to be reversed compared to every other list.Dobruja
@Booby Check getenv("SIMULATOR_MODEL_IDENTIFIER"). It returns the same model identifier that an equivalent device would return.Petras
This list would become even more useful if you would add the screen resolution in the comments.Fujimoto
Not working if device is iPhone 5. Its returning iPhone 6.Meshwork
My app wa rejected because of uidevice-extension ! it uses private API ! Switching to GBDeviceInfo pod...Rayshell
@Rayshell Apple doesn't reject apps because of UIDevice extension, there must some other reason. I've had many apps approved using same Swift 3 code.Hoang
@AniruddhJoshi I was using this library in my application for 4 years, Now suddenly my last update was rejected because some lib is including some private module , don't remember correctly, CoreGraphics or something... I was googling and found somebody already found reference to that module in github.com/erica/uidevice-extension library , so keep it using if you want but how you so confidently write that its not true what I researched already ...Rayshell
@Rayshell If you were still using UIDevice extension by Erica, you may face this issue. That library is almost 7-8 years old. You should rather use the codes I have pasted above.Hoang
Yes I already resolved this, using other lib, sure that is what I was talking about @AniruddhJoshi , that library by Erica caused my app to be rejected... So I believe it should be not proposed to others altogether. There are similar up to date libraries though..Rayshell
@Rayshell It is part of my original answer back in 2012. But I have added a note for that.Hoang
@AniruddhJoshi Can you update this answer to show the values for newer device models that just came out?Left
@AlbertRenshaw Done. I have also added all Apple watch devices IDs, including series 4.Hoang
What is the difference between this and the sysctl.h solution?Nymph
Up-to-date list of devices can be found here: gist.github.com/adamawolf/3048717Radiotherapy
I
140

Expanding on OhhMee's answer above, I added some failsafe to support future devices not (yet) included on the list:

#import <sys/utsname.h>
#import "MyClass.h"

@implementation MyClass
{
    //(your private ivars)
}

- (NSString*) deviceName
{
    struct utsname systemInfo;

    uname(&systemInfo);

    NSString* code = [NSString stringWithCString:systemInfo.machine
                                        encoding:NSUTF8StringEncoding];

    static NSDictionary* deviceNamesByCode = nil;

    if (!deviceNamesByCode) {

        deviceNamesByCode = @{@"i386"      : @"Simulator",
                              @"x86_64"    : @"Simulator",
                              @"iPod1,1"   : @"iPod Touch",        // (Original)
                              @"iPod2,1"   : @"iPod Touch",        // (Second Generation)
                              @"iPod3,1"   : @"iPod Touch",        // (Third Generation)
                              @"iPod4,1"   : @"iPod Touch",        // (Fourth Generation)
                              @"iPod7,1"   : @"iPod Touch",        // (6th Generation)       
                              @"iPhone1,1" : @"iPhone",            // (Original)
                              @"iPhone1,2" : @"iPhone",            // (3G)
                              @"iPhone2,1" : @"iPhone",            // (3GS)
                              @"iPad1,1"   : @"iPad",              // (Original)
                              @"iPad2,1"   : @"iPad 2",            //
                              @"iPad3,1"   : @"iPad",              // (3rd Generation)
                              @"iPhone3,1" : @"iPhone 4",          // (GSM)
                              @"iPhone3,3" : @"iPhone 4",          // (CDMA/Verizon/Sprint)
                              @"iPhone4,1" : @"iPhone 4S",         //
                              @"iPhone5,1" : @"iPhone 5",          // (model A1428, AT&T/Canada)
                              @"iPhone5,2" : @"iPhone 5",          // (model A1429, everything else)
                              @"iPad3,4"   : @"iPad",              // (4th Generation)
                              @"iPad2,5"   : @"iPad Mini",         // (Original)
                              @"iPhone5,3" : @"iPhone 5c",         // (model A1456, A1532 | GSM)
                              @"iPhone5,4" : @"iPhone 5c",         // (model A1507, A1516, A1526 (China), A1529 | Global)
                              @"iPhone6,1" : @"iPhone 5s",         // (model A1433, A1533 | GSM)
                              @"iPhone6,2" : @"iPhone 5s",         // (model A1457, A1518, A1528 (China), A1530 | Global)
                              @"iPhone7,1" : @"iPhone 6 Plus",     //
                              @"iPhone7,2" : @"iPhone 6",          //
                              @"iPhone8,1" : @"iPhone 6S",         //
                              @"iPhone8,2" : @"iPhone 6S Plus",    //
                              @"iPhone8,4" : @"iPhone SE",         //
                              @"iPhone9,1" : @"iPhone 7",          //
                              @"iPhone9,3" : @"iPhone 7",          //
                              @"iPhone9,2" : @"iPhone 7 Plus",     //
                              @"iPhone9,4" : @"iPhone 7 Plus",     //
                              @"iPhone10,1": @"iPhone 8",          // CDMA
                              @"iPhone10,4": @"iPhone 8",          // GSM
                              @"iPhone10,2": @"iPhone 8 Plus",     // CDMA
                              @"iPhone10,5": @"iPhone 8 Plus",     // GSM
                              @"iPhone10,3": @"iPhone X",          // CDMA
                              @"iPhone10,6": @"iPhone X",          // GSM
                              @"iPhone11,2": @"iPhone XS",         //
                              @"iPhone11,4": @"iPhone XS Max",     //
                              @"iPhone11,6": @"iPhone XS Max",     // China
                              @"iPhone11,8": @"iPhone XR",         //
                              @"iPhone12,1": @"iPhone 11",         //
                              @"iPhone12,3": @"iPhone 11 Pro",     //
                              @"iPhone12,5": @"iPhone 11 Pro Max", //

                              @"iPad4,1"   : @"iPad Air",          // 5th Generation iPad (iPad Air) - Wifi
                              @"iPad4,2"   : @"iPad Air",          // 5th Generation iPad (iPad Air) - Cellular
                              @"iPad4,4"   : @"iPad Mini",         // (2nd Generation iPad Mini - Wifi)
                              @"iPad4,5"   : @"iPad Mini",         // (2nd Generation iPad Mini - Cellular)
                              @"iPad4,7"   : @"iPad Mini",         // (3rd Generation iPad Mini - Wifi (model A1599))
                              @"iPad6,7"   : @"iPad Pro (12.9\")", // iPad Pro 12.9 inches - (model A1584) 
                              @"iPad6,8"   : @"iPad Pro (12.9\")", // iPad Pro 12.9 inches - (model A1652) 
                              @"iPad6,3"   : @"iPad Pro (9.7\")",  // iPad Pro 9.7 inches - (model A1673)
                              @"iPad6,4"   : @"iPad Pro (9.7\")"   // iPad Pro 9.7 inches - (models A1674 and A1675)
                              };
    }

    NSString* deviceName = [deviceNamesByCode objectForKey:code];

    if (!deviceName) {
        // Not found on database. At least guess main device type from string contents:

        if ([code rangeOfString:@"iPod"].location != NSNotFound) {
            deviceName = @"iPod Touch";
        }
        else if([code rangeOfString:@"iPad"].location != NSNotFound) {
            deviceName = @"iPad";
        }
        else if([code rangeOfString:@"iPhone"].location != NSNotFound){
            deviceName = @"iPhone";
        }
        else {
            deviceName = @"Unknown";
        }
    }

    return deviceName;
}

// (rest of class implementation omitted)

@end

I also omitted the detailed information (e.g. "model A1507, A1516, A1526 (China), A1529 | Global") and placed it in the comments instead, in case you want to use this as user-facing strings and not freak them out.


Edit: This answer provides a similar implementation using Swift 2.

Edit 2: I just added the iPad Pro models (both sizes). For future reference, the model numbers/etc. can be found in The iPhone Wiki.

Edit 3: Add support for iPhone XS, iPhone XS Max and iPhone XR.

Edit 4: Add support for iPhone 11, iPhone 11 Pro and iPhone 11 Pro Max.

Isbell answered 19/11, 2013 at 2:44 Comment(6)
I was mistakenly searching for the strings "iPhone", "iPad" and "iPod" inside deviceName, when I intended to search code. Someone suggested an edit but I couldn't approve it before some other people rejected it, so I corrected the answer myself. Thanks to whoever suggested it.Isbell
@NicolasMiari I have added missing stuff.Jehoshaphat
is Code unique. There is no official documentation for the systemInfo.machine. Will the identifier like "iPhone7,2" will always be unique for @"iPhone 6" or it can change in future.Spector
@AshishPisey No idea. It doesn’t seem to have changed in a while, and it feels like it won’t. Everyone is using this API though; I’m not aware of any other means...Isbell
Up-to-date list of devices can be found here: gist.github.com/adamawolf/3048717Radiotherapy
What about the newly released iPhone SE2 model?Jehoshaphat
N
48

I've made the plist file to help you to get the complete name for each device (source code right at the end of my answer)

Based on OhhMee's answer, you can use it like this:

Swift 4.0

static func deviceName() -> String {

        var systemInfo = utsname()
        uname(&systemInfo)

        guard let iOSDeviceModelsPath = Bundle.main.path(forResource: "iOSDeviceModelMapping", ofType: "plist") else { return "" }
        guard let iOSDevices = NSDictionary(contentsOfFile: iOSDeviceModelsPath) else { return "" }

        let machineMirror = Mirror(reflecting: systemInfo.machine)
        let identifier = machineMirror.children.reduce("") { identifier, element in
            guard let value = element.value as? Int8, value != 0 else { return identifier }
            return identifier + String(UnicodeScalar(UInt8(value)))
        }

        return iOSDevices.value(forKey: identifier) as! String
    }

Don't forget to add #import <sys/utsname.h> in your Bridging Header.

Objective C

#import <sys/utsname.h>

NSString *machineName()
{
    struct utsname systemInfo;
    uname(&systemInfo);

    NSString *iOSDeviceModelsPath = [[NSBundle mainBundle] pathForResource:@"iOSDeviceModelMapping" ofType:@"plist"];
    NSDictionary *iOSDevices = [NSDictionary dictionaryWithContentsOfFile:iOSDeviceModelsPath];

    NSString* deviceModel = [NSString stringWithCString:systemInfo.machine
                                               encoding:NSUTF8StringEncoding];

    return [iOSDevices valueForKey:deviceModel];
}

The plist file :

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>x86_64</key>
    <string>Simulator</string>
    <key>i386</key>
    <string>Simulator</string>
    <key>iPod1,1</key>
    <string>iPod Touch 1st Gen</string>
    <key>iPod2,1</key>
    <string>iPod Touch 2nd Gen</string>
    <key>iPod3,1</key>
    <string>iPod Touch 3rd Gen</string>
    <key>iPod4,1</key>
    <string>iPod Touch 4th Gen</string>
    <key>iPod5,1</key>
    <string>iPod Touch 5th Gen</string>
    <key>iPod7,1</key>
    <string>iPod Touch 6th Gen</string>
    <key>iPhone1,1</key>
    <string>iPhone</string>
    <key>iPhone1,2</key>
    <string>iPhone 3G</string>
    <key>iPhone2,1</key>
    <string>iPhone 3GS</string>
    <key>iPhone3,1</key>
    <string>iPhone 4</string>
    <key>iPhone3,2</key>
    <string>iPhone 4</string>
    <key>iPhone3,3</key>
    <string>iPhone 4</string>
    <key>iPhone4,1</key>
    <string>iPhone 4S</string>
    <key>iPhone5,1</key>
    <string>iPhone 5 model A1428</string>
    <key>iPhone5,2</key>
    <string>iPhone 5 model A1429</string>
    <key>iPhone5,3</key>
    <string>iPhone 5C</string>
    <key>iPhone5,4</key>
    <string>iPhone 5C</string>
    <key>iPhone6,1</key>
    <string>iPhone 5S</string>
    <key>iPhone6,2</key>
    <string>iPhone 5S</string>
    <key>iPhone7,2</key>
    <string>iPhone 6</string>
    <key>iPhone7,1</key>
    <string>iPhone 6 Plus</string>
    <key>iPhone8,1</key>
    <string>iPhone 6S</string>
    <key>iPhone8,2</key>
    <string>iPhone 6S Plus</string>
    <key>iPhone8,4</key>
    <string>iPhone SE</string>
    <key>iPhone9,1</key>
    <string>iPhone 7</string>
    <key>iPhone9,2</key>
    <string>iPhone 7 Plus</string>
    <key>iPhone9,3</key>
    <string>iPhone 7</string>
    <key>iPhone9,4</key>
    <string>iPhone 7 Plus</string>
    <key>iPhone10,1</key>
    <string>iPhone 8</string>
    <key>iPhone10,4</key>
    <string>iPhone 8</string>
    <key>iPhone10,2</key>
    <string>iPhone 8 Plus</string>
    <key>iPhone10,5</key>
    <string>iPhone 8 Plus</string>
    <key>iPhone10,3</key>
    <string>iPhone X</string>
    <key>iPhone10,6</key>
    <string>iPhone X</string>
    <key>iPhone11,2</key>
    <string>iPhone XS</string>
    <key>iPhone11,4</key>
    <string>iPhone XS Max</string>
    <key>iPhone11,6</key>
    <string>iPhone XS Max</string>
    <key>iPhone11,8</key>
    <string>iPhone XR</string>
    <key>iPad1,1</key>
    <string>iPad</string>
    <key>iPad2,1</key>
    <string>iPad 2</string>
    <key>iPad2,2</key>
    <string>iPad 2</string>
    <key>iPad2,3</key>
    <string>iPad 2</string>
    <key>iPad2,4</key>
    <string>iPad 2</string>
    <key>iPad3,1</key>
    <string>iPad 3rd Gen</string>
    <key>iPad3,2</key>
    <string>iPad 3rd Gen</string>
    <key>iPad3,3</key>
    <string>iPad 3rd Gen</string>
    <key>iPad3,4</key>
    <string>iPad 4th Gen</string>
    <key>iPad3,5</key>
    <string>iPad 4th Gen</string>
    <key>iPad3,6</key>
    <string>iPad 4th Gen</string>
    <key>iPad4,1</key>
    <string>iPad Air</string>
    <key>iPad4,2</key>
    <string>iPad Air</string>
    <key>iPad4,3</key>
    <string>iPad Air</string>
    <key>iPad2,5</key>
    <string>iPad Mini 1st Gen</string>
    <key>iPad2,6</key>
    <string>iPad Mini 1st Gen</string>
    <key>iPad2,7</key>
    <string>iPad Mini 1st Gen</string>
    <key>iPad4,4</key>
    <string>iPad Mini 2nd Gen</string>
    <key>iPad4,5</key>
    <string>iPad Mini 2nd Gen</string>
    <key>iPad4,6</key>
    <string>iPad Mini 2nd Gen</string>
    <key>iPad4,7</key>
    <string>iPad Mini 3rd Gen</string>
    <key>iPad4,8</key>
    <string>iPad Mini 3rd Gen</string>
    <key>iPad4,9</key>
    <string>iPad Mini 3rd Gen</string>
    <key>iPad5,1</key>
    <string>iPad Mini 4</string>
    <key>iPad5,2</key>
    <string>iPad Mini 4</string>
    <key>iPad5,3</key>
    <string>iPad Air 2</string>
    <key>iPad5,4</key>
    <string>iPad Air 2</string>
    <key>iPad6,3</key>
    <string>iPad Pro 9.7 inch</string>
    <key>iPad6,4</key>
    <string>iPad Pro 9.7 inch</string>
    <key>iPad6,7</key>
    <string>iPad Pro 12.9 inch</string>
    <key>iPad6,8</key>
    <string>iPad Pro 12.9 inch</string>
    <key>iPad7,1</key>
    <string>iPad Pro 12.9 inch 2nd Gen</string>
    <key>iPad7,2</key>
    <string>iPad Pro 12.9 inch 2nd Gen</string>
    <key>iPad7,3</key>
    <string>iPad Pro 10.5 inch</string>
    <key>iPad7,4</key>
    <string>iPad Pro 10.5 inch</string>
    <key>iPad8,1</key>
    <string>iPad Pro 11 inch</string>
    <key>iPad8,2</key>
    <string>iPad Pro 11 inch</string>
    <key>iPad8,3</key>
    <string>iPad Pro 11 inch</string>
    <key>iPad8,4</key>
    <string>iPad Pro 11 inch</string>
    <key>iPad8,5</key>
    <string>iPad Pro 12.9 inch 3rd Gen</string>
    <key>iPad8,6</key>
    <string>iPad Pro 12.9 inch 3rd Gen</string>
    <key>iPad8,7</key>
    <string>iPad Pro 12.9 inch 3rd Gen</string>
    <key>iPad8,8</key>
    <string>iPad Pro 12.9 inch 3rd Gen</string>
</dict>
</plist>
Nucellus answered 15/7, 2013 at 13:47 Comment(9)
updated with latest devices (iPhone 6S, iPad Pro, etc)Nucellus
Please inline the contents of your plist file within your answer (hopefully, formatted as code). The same rules that apply to link-only answers apply to an essential file stored outside of SO: it could vanish some day.Isbell
Updated with latest devices: iPhone 8 (Plus), iPhone X, iPad Pro 12.9 inch 2nd Gen, iPad Pro 10.5 inchBibliography
Updated with new devices: iPhone XS, XS Max and XRBibliography
Thanks a lot @vilmoskörte !Nucellus
@vilmoskörte I couldn't find the iPhone XS, XS Max and XR devices in the plist. Where did you add them?Betatron
Oops, somehow they are lost. Re-added them, just wait a bit until they are approved by peer review.Bibliography
Approved. Sorry for the delay and thanks for the update @vilmoskörteNucellus
added ipad pro 3rd generations (iPad 8,1 to iPad 8,8) to the plistMisfile
Z
21

[[UIDevice currentDevice] model] just returns iPhone or iPod, you don't get the numbers of the model that would let you differentiate between different generations of devices.

Code this method:

#include <sys/sysctl.h>
...

+ (NSString *)getModel {
    size_t size;
    sysctlbyname("hw.machine", NULL, &size, NULL, 0);
    char *model = malloc(size);
    sysctlbyname("hw.machine", model, &size, NULL, 0);
    NSString *deviceModel = [NSString stringWithCString:model encoding:NSUTF8StringEncoding];
    free(model);
    return deviceModel;
}

And call the method [self getModel] whenever you need the model and you'll get i.e: "iPhone5,1" for the ridiculously thin and speedy iPhone 5.

One good practice is to create a class called Utils.h/Utils.m and put methods like getModel there so you can get this info from anywhere in your App simply by importing the class and invoking [Utils getModel];

Zetes answered 3/10, 2012 at 18:18 Comment(0)
S
14

Below is the code for that (code may not contain all device's string, I'm with other guys are maintaining the same code on GitHub so please take the latest code from there)

Objective-C : GitHub/DeviceUtil

Swift : GitHub/DeviceGuru


#include <sys/types.h>
#include <sys/sysctl.h>

- (NSString*)hardwareDescription {
    NSString *hardware = [self hardwareString];
    if ([hardware isEqualToString:@"iPhone1,1"]) return @"iPhone 2G";
    if ([hardware isEqualToString:@"iPhone1,2"]) return @"iPhone 3G";
    if ([hardware isEqualToString:@"iPhone3,1"]) return @"iPhone 4";
    if ([hardware isEqualToString:@"iPhone4,1"]) return @"iPhone 4S";
    if ([hardware isEqualToString:@"iPhone5,1"]) return @"iPhone 5";
    if ([hardware isEqualToString:@"iPod1,1"]) return @"iPodTouch 1G";
    if ([hardware isEqualToString:@"iPod2,1"]) return @"iPodTouch 2G";
    if ([hardware isEqualToString:@"iPad1,1"]) return @"iPad";
    if ([hardware isEqualToString:@"iPad2,6"]) return @"iPad Mini";
    if ([hardware isEqualToString:@"iPad4,1"]) return @"iPad Air WIFI";
    //there are lots of other strings too, checkout the github repo
    //link is given at the top of this answer

    if ([hardware isEqualToString:@"i386"]) return @"Simulator";
    if ([hardware isEqualToString:@"x86_64"]) return @"Simulator";

    return nil;
}

- (NSString*)hardwareString {
    size_t size = 100;
    char *hw_machine = malloc(size);
    int name[] = {CTL_HW,HW_MACHINE};
    sysctl(name, 2, hw_machine, &size, NULL, 0);
    NSString *hardware = [NSString stringWithUTF8String:hw_machine];
    free(hw_machine);
    return hardware;
}
Steed answered 13/4, 2015 at 6:33 Comment(0)
O
13

A category for going getting away from the NSString description

In general, it is desirable to avoid arbitrary string comparisons throughout your code. It is better to update the strings in one place and hide the magic string from your app. I provide a category on UIDevice for that purpose.

For my specific needs I need to know which device I am using without the need to know specifics about networking capability that can be easily retrieved in other ways. So you will find a coarser grained enum than the ever growing list of devices.

Updating is a matter of adding the device to the enum and the lookup table.

UIDevice+NTNUExtensions.h

typedef NS_ENUM(NSUInteger, NTNUDeviceType) {
    DeviceAppleUnknown,
    DeviceAppleSimulator,
    DeviceAppleiPhone,
    DeviceAppleiPhone3G,
    DeviceAppleiPhone3GS,
    DeviceAppleiPhone4,
    DeviceAppleiPhone4S,
    DeviceAppleiPhone5,
    DeviceAppleiPhone5C,
    DeviceAppleiPhone5S,
    DeviceAppleiPhone6,
    DeviceAppleiPhone6_Plus,
    DeviceAppleiPhone6S,
    DeviceAppleiPhone6S_Plus,
    DeviceAppleiPhoneSE,
    DeviceAppleiPhone7,
    DeviceAppleiPhone7_Plus,
    DeviceAppleiPodTouch,
    DeviceAppleiPodTouch2G,
    DeviceAppleiPodTouch3G,
    DeviceAppleiPodTouch4G,
    DeviceAppleiPad,
    DeviceAppleiPad2,
    DeviceAppleiPad3G,
    DeviceAppleiPad4G,
    DeviceAppleiPad5G_Air,
    DeviceAppleiPadMini,
    DeviceAppleiPadMini2G,
    DeviceAppleiPadPro12,
    DeviceAppleiPadPro9
};



@interface UIDevice (NTNUExtensions)

- (NSString *)ntnu_deviceDescription;
- (NTNUDeviceType)ntnu_deviceType;

@end

UIDevice+NTNUExtensions.m

#import <sys/utsname.h>
#import "UIDevice+NTNUExtensions.h"

@implementation UIDevice (NTNUExtensions)

- (NSString *)ntnu_deviceDescription
{
    struct utsname systemInfo;
    uname(&systemInfo);

    return [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
}

- (NTNUDeviceType)ntnu_deviceType
{
    NSNumber *deviceType = [[self ntnu_deviceTypeLookupTable] objectForKey:[self ntnu_deviceDescription]];
    return [deviceType unsignedIntegerValue];
}

- (NSDictionary *)ntnu_deviceTypeLookupTable
{
    return @{
             @"i386": @(DeviceAppleSimulator),
             @"x86_64": @(DeviceAppleSimulator),
             @"iPod1,1": @(DeviceAppleiPodTouch),
             @"iPod2,1": @(DeviceAppleiPodTouch2G),
             @"iPod3,1": @(DeviceAppleiPodTouch3G),
             @"iPod4,1": @(DeviceAppleiPodTouch4G),
             @"iPhone1,1": @(DeviceAppleiPhone),
             @"iPhone1,2": @(DeviceAppleiPhone3G),
             @"iPhone2,1": @(DeviceAppleiPhone3GS),
             @"iPhone3,1": @(DeviceAppleiPhone4),
             @"iPhone3,3": @(DeviceAppleiPhone4),
             @"iPhone4,1": @(DeviceAppleiPhone4S),
             @"iPhone5,1": @(DeviceAppleiPhone5),
             @"iPhone5,2": @(DeviceAppleiPhone5),
             @"iPhone5,3": @(DeviceAppleiPhone5C),
             @"iPhone5,4": @(DeviceAppleiPhone5C),
             @"iPhone6,1": @(DeviceAppleiPhone5S),
             @"iPhone6,2": @(DeviceAppleiPhone5S),
             @"iPhone7,1": @(DeviceAppleiPhone6_Plus),
             @"iPhone7,2": @(DeviceAppleiPhone6),
             @"iPhone8,1" :@(DeviceAppleiPhone6S),
             @"iPhone8,2" :@(DeviceAppleiPhone6S_Plus),
             @"iPhone8,4" :@(DeviceAppleiPhoneSE),
             @"iPhone9,1" :@(DeviceAppleiPhone7),
             @"iPhone9,3" :@(DeviceAppleiPhone7),
             @"iPhone9,2" :@(DeviceAppleiPhone7_Plus),
             @"iPhone9,4" :@(DeviceAppleiPhone7_Plus),
             @"iPad1,1": @(DeviceAppleiPad),
             @"iPad2,1": @(DeviceAppleiPad2),
             @"iPad3,1": @(DeviceAppleiPad3G),
             @"iPad3,4": @(DeviceAppleiPad4G),
             @"iPad2,5": @(DeviceAppleiPadMini),
             @"iPad4,1": @(DeviceAppleiPad5G_Air),
             @"iPad4,2": @(DeviceAppleiPad5G_Air),
             @"iPad4,4": @(DeviceAppleiPadMini2G),
             @"iPad4,5": @(DeviceAppleiPadMini2G),
             @"iPad4,7":@(DeviceAppleiPadMini),
             @"iPad6,7":@(DeviceAppleiPadPro12),
             @"iPad6,8":@(DeviceAppleiPadPro12),
             @"iPad6,3":@(DeviceAppleiPadPro9),
             @"iPad6,4":@(DeviceAppleiPadPro9)
             };
}

@end
Oleander answered 1/2, 2015 at 10:56 Comment(1)
This a nice solution. A useful extension of this is to sort the enum based on the device’s processor which let’s you use a simple < or > comparison to determine if a device is less or more powerful than your target. For example, if you want to limit background animations on devices coming before the iPhone 4S.Espadrille
H
12

I've optimized NicolasMiari's implementation, and added Simulator, here:

+ (NSString*)deviceName {

  static NSDictionary* deviceNamesByCode = nil;
  static NSString* deviceName = nil;

  if (deviceName) {
    return deviceName;
  }

  deviceNamesByCode = @{
    @"i386"      :@"Simulator",
    @"iPod1,1"   :@"iPod Touch",      // (Original)
    @"iPod2,1"   :@"iPod Touch",      // (Second Generation)
    @"iPod3,1"   :@"iPod Touch",      // (Third Generation)
    @"iPod4,1"   :@"iPod Touch",      // (Fourth Generation)
    @"iPhone1,1" :@"iPhone",          // (Original)
    @"iPhone1,2" :@"iPhone",          // (3G)
    @"iPhone2,1" :@"iPhone",          // (3GS)
    @"iPad1,1"   :@"iPad",            // (Original)
    @"iPad2,1"   :@"iPad 2",          //
    @"iPad3,1"   :@"iPad",            // (3rd Generation)
    @"iPhone3,1" :@"iPhone 4",        //
    @"iPhone4,1" :@"iPhone 4S",       //
    @"iPhone5,1" :@"iPhone 5",        // (model A1428, AT&T/Canada)
    @"iPhone5,2" :@"iPhone 5",        // (model A1429, everything else)
    @"iPad3,4"   :@"iPad",            // (4th Generation)
    @"iPad2,5"   :@"iPad Mini",       // (Original)
    @"iPhone5,3" :@"iPhone 5c",       // (model A1456, A1532 | GSM)
    @"iPhone5,4" :@"iPhone 5c",       // (model A1507, A1516, A1526 (China), A1529 | Global)
    @"iPhone6,1" :@"iPhone 5s",       // (model A1433, A1533 | GSM)
    @"iPhone6,2" :@"iPhone 5s",       // (model A1457, A1518, A1528 (China), A1530 | Global)
    @"iPad4,1"   :@"iPad Air",        // 5th Generation iPad (iPad Air) - Wifi
    @"iPad4,2"   :@"iPad Air",        // 5th Generation iPad (iPad Air) - Cellular
    @"iPad4,4"   :@"iPad Mini",       // (2nd Generation iPad Mini - Wifi)
    @"iPad4,5"   :@"iPad Mini"        // (2nd Generation iPad Mini - Cellular)
  };

  struct utsname systemInfo;
  uname(&systemInfo);
  NSString* code = [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];

  deviceName = [deviceNamesByCode objectForKey:code];

  if (!deviceName) {
    // Not found in database. At least guess main device type from string contents:

    if ([code rangeOfString:@"iPod"].location != NSNotFound) {
      deviceName = @"iPod Touch";
    } else if([code rangeOfString:@"iPad"].location != NSNotFound) {
      deviceName = @"iPad";
    } else if([code rangeOfString:@"iPhone"].location != NSNotFound){
      deviceName = @"iPhone";
    } else {
      deviceName = @"Simulator";
    }
  }

  return deviceName;
}

```

Helmand answered 24/6, 2014 at 14:35 Comment(2)
We need to turn this into a GitHub repo, and update it everytime new iPhones/iPads/etc. get added to the line up!Isbell
Perhaps even a cocoapodHelmand
G
11

Add a new file with following code and simply call UIDevice.modelName This consists of all models released till date including iPhone 13 series and in Swift 5.0

import UIKit
import SystemConfiguration

public extension UIDevice {
    static let modelName: String = {
        var systemInfo = utsname()
        uname(&systemInfo)
        let machineMirror = Mirror(reflecting: systemInfo.machine)
        let identifier = machineMirror.children.reduce("") { identifier, element in
            guard let value = element.value as? Int8, value != 0 else { return identifier }
            return identifier + String(UnicodeScalar(UInt8(value)))
        }
        
        let deviceMapping = ["i386": "iPhone Simulator",
         "x86_64": "iPhone Simulator",
         "arm64": "iPhone Simulator",
         "iPhone1,1": "iPhone",
         "iPhone1,2": "iPhone 3G",
         "iPhone2,1": "iPhone 3GS",
         "iPhone3,1": "iPhone 4",
         "iPhone3,2": "iPhone 4 GSM Rev A",
         "iPhone3,3": "iPhone 4 CDMA",
         "iPhone4,1": "iPhone 4S",
         "iPhone5,1": "iPhone 5 (GSM)",
         "iPhone5,2": "iPhone 5 (GSM+CDMA)",
         "iPhone5,3": "iPhone 5C (GSM)",
         "iPhone5,4": "iPhone 5C (Global)",
         "iPhone6,1": "iPhone 5S (GSM)",
         "iPhone6,2": "iPhone 5S (Global)",
         "iPhone7,1": "iPhone 6 Plus",
         "iPhone7,2": "iPhone 6",
         "iPhone8,1": "iPhone 6s",
         "iPhone8,2": "iPhone 6s Plus",
         "iPhone8,4": "iPhone SE (GSM)",
         "iPhone9,1": "iPhone 7",
         "iPhone9,2": "iPhone 7 Plus",
         "iPhone9,3": "iPhone 7",
         "iPhone9,4": "iPhone 7 Plus",
         "iPhone10,1": "iPhone 8",
         "iPhone10,2": "iPhone 8 Plus",
         "iPhone10,3": "iPhone X Global",
         "iPhone10,4": "iPhone 8",
         "iPhone10,5": "iPhone 8 Plus",
         "iPhone10,6": "iPhone X GSM",
         "iPhone11,2": "iPhone XS",
         "iPhone11,4": "iPhone XS Max",
         "iPhone11,6": "iPhone XS Max Global",
         "iPhone11,8": "iPhone XR",
         "iPhone12,1": "iPhone 11",
         "iPhone12,3": "iPhone 11 Pro",
         "iPhone12,5": "iPhone 11 Pro Max",
         "iPhone12,8": "iPhone SE 2nd Gen",
         "iPhone13,1": "iPhone 12 Mini",
         "iPhone13,2": "iPhone 12",
         "iPhone13,3": "iPhone 12 Pro",
         "iPhone13,4": "iPhone 12 Pro Max",
         "iPhone14,2": "iPhone 13 Pro",
         "iPhone14,3": "iPhone 13 Pro Max",
         "iPhone14,4": "iPhone 13 Mini",
         "iPhone14,5": "iPhone 13",
         "iPod1,1": "1st Gen iPod",
         "iPod2,1": "2nd Gen iPod",
         "iPod3,1": "3rd Gen iPod",
         "iPod4,1": "4th Gen iPod",
         "iPod5,1": "5th Gen iPod",
         "iPod7,1": "6th Gen iPod",
         "iPod9,1": "7th Gen iPod",
         "iPad1,1": "iPad",
         "iPad1,2": "iPad 3G",
         "iPad2,1": "2nd Gen iPad",
         "iPad2,2": "2nd Gen iPad GSM",
         "iPad2,3": "2nd Gen iPad CDMA",
         "iPad2,4": "2nd Gen iPad New Revision",
         "iPad3,1": "3rd Gen iPad",
         "iPad3,2": "3rd Gen iPad CDMA",
         "iPad3,3": "3rd Gen iPad GSM",
         "iPad2,5": "iPad mini",
         "iPad2,6": "iPad mini GSM+LTE",
         "iPad2,7": "iPad mini CDMA+LTE",
         "iPad3,4": "4th Gen iPad",
         "iPad3,5": "4th Gen iPad GSM+LTE",
         "iPad3,6": "4th Gen iPad CDMA+LTE",
         "iPad4,1": "iPad Air (WiFi)",
         "iPad4,2": "iPad Air (GSM+CDMA)",
         "iPad4,3": "1st Gen iPad Air (China)",
         "iPad4,4": "iPad mini Retina (WiFi)",
         "iPad4,5": "iPad mini Retina (GSM+CDMA)",
         "iPad4,6": "iPad mini Retina (China)",
         "iPad4,7": "iPad mini 3 (WiFi)",
         "iPad4,8": "iPad mini 3 (GSM+CDMA)",
         "iPad4,9": "iPad Mini 3 (China)",
         "iPad5,1": "iPad mini 4 (WiFi)",
         "iPad5,2": "4th Gen iPad mini (WiFi+Cellular)",
         "iPad5,3": "iPad Air 2 (WiFi)",
         "iPad5,4": "iPad Air 2 (Cellular)",
         "iPad6,3": "iPad Pro (9.7 inch, WiFi)",
         "iPad6,4": "iPad Pro (9.7 inch, WiFi+LTE)",
         "iPad6,7": "iPad Pro (12.9 inch, WiFi)",
         "iPad6,8": "iPad Pro (12.9 inch, WiFi+LTE)",
         "iPad6,11": "iPad (2017)",
         "iPad6,12": "iPad (2017)",
         "iPad7,1": "iPad Pro 2nd Gen (WiFi)",
         "iPad7,2": "iPad Pro 2nd Gen (WiFi+Cellular)",
         "iPad7,3": "iPad Pro 10.5-inch",
         "iPad7,4": "iPad Pro 10.5-inch",
         "iPad7,5": "iPad 6th Gen (WiFi)",
         "iPad7,6": "iPad 6th Gen (WiFi+Cellular)",
         "iPad7,11": "iPad 7th Gen 10.2-inch (WiFi)",
         "iPad7,12": "iPad 7th Gen 10.2-inch (WiFi+Cellular)",
         "iPad8,1": "iPad Pro 11 inch 3rd Gen (WiFi)",
         "iPad8,2": "iPad Pro 11 inch 3rd Gen (1TB, WiFi)",
         "iPad8,3": "iPad Pro 11 inch 3rd Gen (WiFi+Cellular)",
         "iPad8,4": "iPad Pro 11 inch 3rd Gen (1TB, WiFi+Cellular)",
         "iPad8,5": "iPad Pro 12.9 inch 3rd Gen (WiFi)",
         "iPad8,6": "iPad Pro 12.9 inch 3rd Gen (1TB, WiFi)",
         "iPad8,7": "iPad Pro 12.9 inch 3rd Gen (WiFi+Cellular)",
         "iPad8,8": "iPad Pro 12.9 inch 3rd Gen (1TB, WiFi+Cellular)",
         "iPad8,9": "iPad Pro 11 inch 4th Gen (WiFi)",
         "iPad8,10": "iPad Pro 11 inch 4th Gen (WiFi+Cellular)",
         "iPad8,11": "iPad Pro 12.9 inch 4th Gen (WiFi)",
         "iPad8,12": "iPad Pro 12.9 inch 4th Gen (WiFi+Cellular)",
         "iPad11,1": "iPad mini 5th Gen (WiFi)",
         "iPad11,2": "iPad mini 5th Gen",
         "iPad11,3": "iPad Air 3rd Gen (WiFi)",
         "iPad11,4": "iPad Air 3rd Gen",
         "iPad11,6": "iPad 8th Gen (WiFi)",
         "iPad11,7": "iPad 8th Gen (WiFi+Cellular)",
         "iPad13,1": "iPad air 4th Gen (WiFi)",
         "iPad13,2": "iPad air 4th Gen (WiFi+Cellular)",
         "iPad13,4": "iPad Pro 11 inch 3rd Gen",
         "iPad13,5": "iPad Pro 11 inch 3rd Gen",
         "iPad13,6": "iPad Pro 11 inch 3rd Gen",
         "iPad13,7": "iPad Pro 11 inch 3rd Gen",
         "iPad13,8": "iPad Pro 12.9 inch 5th Gen",
         "iPad13,9": "iPad Pro 12.9 inch 5th Gen",
         "iPad13,10": "iPad Pro 12.9 inch 5th Gen",
         "iPad13,11": "iPad Pro 12.9 inch 5th Gen"]
        return deviceMapping[identifier] ?? identifier
    }()
}
Goodill answered 27/11, 2019 at 13:44 Comment(0)
G
9

Device name and Machine Names, based on iOS Real Device Hardware

My solution to this issue is basically looks related to @NicolasMiari answer within this thread. Separate utility class has a predefined set of Device and Machine names and then depending on the real machine name, retrieve the Device Name.

Note: This answer and it's linked GitHub project has been updated to identify current latest iPhones (iPhone 8, 8+, X) as of October 2017. And this works on iOS11 too. Please visit the GitHub repo and see, and give me feedback if something is wrong.

/*
 * Retrieves back the device name or if not the machine name.
 */
+ (NSString*)deviceModelName {
    struct utsname systemInfo;
    uname(&systemInfo);
    NSString *machineName = [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
    
    //MARK: More official list is at
    //http://theiphonewiki.com/wiki/Models
    //MARK: You may just return machineName. Following is for convenience
    
    NSDictionary *commonNamesDictionary =
    @{
      @"i386":     @"i386 Simulator",
      @"x86_64":   @"x86_64 Simulator",

      @"iPhone1,1":    @"iPhone",
      @"iPhone1,2":    @"iPhone 3G",
      @"iPhone2,1":    @"iPhone 3GS",
      @"iPhone3,1":    @"iPhone 4",
      @"iPhone3,2":    @"iPhone 4(Rev A)",
      @"iPhone3,3":    @"iPhone 4(CDMA)",
      @"iPhone4,1":    @"iPhone 4S",
      @"iPhone5,1":    @"iPhone 5(GSM)",
      @"iPhone5,2":    @"iPhone 5(GSM+CDMA)",
      @"iPhone5,3":    @"iPhone 5c(GSM)",
      @"iPhone5,4":    @"iPhone 5c(GSM+CDMA)",
      @"iPhone6,1":    @"iPhone 5s(GSM)",
      @"iPhone6,2":    @"iPhone 5s(GSM+CDMA)",
  
      @"iPhone7,1":    @"iPhone 6+(GSM+CDMA)",
      @"iPhone7,2":    @"iPhone 6(GSM+CDMA)",
  
      @"iPhone8,1":    @"iPhone 6S(GSM+CDMA)",
      @"iPhone8,2":    @"iPhone 6S+(GSM+CDMA)",
      @"iPhone8,4":    @"iPhone SE(GSM+CDMA)",
      @"iPhone9,1":    @"iPhone 7(GSM+CDMA)",
      @"iPhone9,2":    @"iPhone 7+(GSM+CDMA)",
      @"iPhone9,3":    @"iPhone 7(GSM+CDMA)",
      @"iPhone9,4":    @"iPhone 7+(GSM+CDMA)",
  
      @"iPad1,1":  @"iPad",
      @"iPad2,1":  @"iPad 2(WiFi)",
      @"iPad2,2":  @"iPad 2(GSM)",
      @"iPad2,3":  @"iPad 2(CDMA)",
      @"iPad2,4":  @"iPad 2(WiFi Rev A)",
      @"iPad2,5":  @"iPad Mini 1G (WiFi)",
      @"iPad2,6":  @"iPad Mini 1G (GSM)",
      @"iPad2,7":  @"iPad Mini 1G (GSM+CDMA)",
      @"iPad3,1":  @"iPad 3(WiFi)",
      @"iPad3,2":  @"iPad 3(GSM+CDMA)",
      @"iPad3,3":  @"iPad 3(GSM)",
      @"iPad3,4":  @"iPad 4(WiFi)",
      @"iPad3,5":  @"iPad 4(GSM)",
      @"iPad3,6":  @"iPad 4(GSM+CDMA)",
  
      @"iPad4,1":  @"iPad Air(WiFi)",
      @"iPad4,2":  @"iPad Air(GSM)",
      @"iPad4,3":  @"iPad Air(GSM+CDMA)",
  
      @"iPad5,3":  @"iPad Air 2 (WiFi)",
      @"iPad5,4":  @"iPad Air 2 (GSM+CDMA)",
  
      @"iPad4,4":  @"iPad Mini 2G (WiFi)",
      @"iPad4,5":  @"iPad Mini 2G (GSM)",
      @"iPad4,6":  @"iPad Mini 2G (GSM+CDMA)",
  
      @"iPad4,7":  @"iPad Mini 3G (WiFi)",
      @"iPad4,8":  @"iPad Mini 3G (GSM)",
      @"iPad4,9":  @"iPad Mini 3G (GSM+CDMA)",
  
      @"iPod1,1":  @"iPod 1st Gen",
      @"iPod2,1":  @"iPod 2nd Gen",
      @"iPod3,1":  @"iPod 3rd Gen",
      @"iPod4,1":  @"iPod 4th Gen",
      @"iPod5,1":  @"iPod 5th Gen",
      @"iPod7,1":  @"iPod 6th Gen",
      };
    
    NSString *deviceName = commonNamesDictionary[machineName];
    
    if (deviceName == nil) {
        deviceName = machineName;
    }
    
    return deviceName;
}

I have added this implementation and few other convenient utility methods in a class and put it out there in this GitHub Repository. And also you can find the up to date device information list within this Wiki page.

Please visit it and get use of it.

Update:

You may requires to import sys framework,

#import <sys/utsname.h>
Guttapercha answered 29/6, 2016 at 10:28 Comment(1)
Kasun, thanks for the updated implementation of this. Please try to keep it updated for new models in future.Angieangil
W
7

Swift 3 compatible

// MARK: - UIDevice Extension -

private let DeviceList = [
/* iPod 5 */          "iPod5,1": "iPod Touch 5",
/* iPhone 4 */        "iPhone3,1":  "iPhone 4", "iPhone3,2": "iPhone 4", "iPhone3,3": "iPhone 4",
/* iPhone 4S */       "iPhone4,1": "iPhone 4S",
/* iPhone 5 */        "iPhone5,1": "iPhone 5", "iPhone5,2": "iPhone 5",
/* iPhone 5C */       "iPhone5,3": "iPhone 5C", "iPhone5,4": "iPhone 5C",
/* iPhone 5S */       "iPhone6,1": "iPhone 5S", "iPhone6,2": "iPhone 5S",
/* iPhone 6 */        "iPhone7,2": "iPhone 6",
/* iPhone 6 Plus */   "iPhone7,1": "iPhone 6 Plus",
/* iPhone 6S */       "iPhone8,1": "iPhone 6S",
/* iPhone 6S Plus */  "iPhone8,2": "iPhone 6S Plus",
/* iPhone SE */       "iPhone8,4": "iPhone SE",
/* iPhone 7 */        "iPhone9,1": "iPhone 7",
/* iPhone 7 */        "iPhone9,3": "iPhone 7",
/* iPhone 7 Plus */   "iPhone9,2": "iPhone 7 Plus",
/* iPhone 7 Plus */   "iPhone9,4": "iPhone 7 Plus",
/* iPad 2 */          "iPad2,1": "iPad 2", "iPad2,2": "iPad 2", "iPad2,3": "iPad 2", "iPad2,4": "iPad 2",
/* iPad 3 */          "iPad3,1": "iPad 3", "iPad3,2": "iPad 3", "iPad3,3":     "iPad 3",
/* iPad 4 */          "iPad3,4": "iPad 4", "iPad3,5": "iPad 4", "iPad3,6": "iPad 4",
/* iPad Air */        "iPad4,1": "iPad Air", "iPad4,2": "iPad Air", "iPad4,3": "iPad Air",
/* iPad Air 2 */      "iPad5,1": "iPad Air 2", "iPad5,3": "iPad Air 2", "iPad5,4": "iPad Air 2",
/* iPad Mini */       "iPad2,5": "iPad Mini 1", "iPad2,6": "iPad Mini 1", "iPad2,7": "iPad Mini 1",
/* iPad Mini 2 */     "iPad4,4": "iPad Mini 2", "iPad4,5": "iPad Mini 2", "iPad4,6": "iPad Mini 2",
/* iPad Mini 3 */     "iPad4,7": "iPad Mini 3", "iPad4,8": "iPad Mini 3", "iPad4,9": "iPad Mini 3",
/* iPad Pro 12.9 */   "iPad6,7": "iPad Pro 12.9", "iPad6,8": "iPad Pro 12.9",
/* iPad Pro  9.7 */   "iPad6,3": "iPad Pro 9.7", "iPad6,4": "iPad Pro 9.7",
/* Simulator */       "x86_64": "Simulator", "i386": "Simulator"
]

extension UIDevice {

    static var modelName: String {
        var systemInfo = utsname()
        uname(&systemInfo)

        let machine = systemInfo.machine
        let mirror = Mirror(reflecting: machine)

        var identifier = ""

        for child in mirror.children {
            if let value = child.value as? Int8, value != 0 {
                identifier += String(UnicodeScalar(UInt8(value)))
            }
        }
        return DeviceList[identifier] ?? identifier
    }

    static var isIphone4: Bool {
        return modelName == "iPhone 5" || modelName == "iPhone 5C" || modelName == "iPhone 5S" || UIDevice.isSimulatorIPhone4
    }

    static var isIphone5: Bool {
        return modelName == "iPhone 4S" || modelName == "iPhone 4" || UIDevice.isSimulatorIPhone5
    }

    static var isIphone6: Bool {
        return modelName == "iPhone 6" || UIDevice.isSimulatorIPhone6
    }
    static var isIphone6Plus: Bool {
        return modelName == "iPhone 6 Plus" || UIDevice.isSimulatorIPhone6Plus
    }

    static var isIpad: Bool {
        if UIDevice.current.model.contains("iPad") {
            return true
        }
        return false
    }

    static var isIphone: Bool {
        return !self.isIpad
    }

    /// Check if current device is iPhone4S (and earlier) relying on screen heigth
    static var isSimulatorIPhone4: Bool {
        return UIDevice.isSimulatorWithScreenHeigth(480)
    }

    /// Check if current device is iPhone5 relying on screen heigth
    static var isSimulatorIPhone5: Bool {
        return UIDevice.isSimulatorWithScreenHeigth(568)
    }

    /// Check if current device is iPhone6 relying on screen heigth
    static var isSimulatorIPhone6: Bool {
        return UIDevice.isSimulatorWithScreenHeigth(667)
    }

    /// Check if current device is iPhone6 Plus relying on screen heigth
    static var isSimulatorIPhone6Plus: Bool {
        return UIDevice.isSimulatorWithScreenHeigth(736)
    }

    private static func isSimulatorWithScreenHeigth(_ heigth: CGFloat) -> Bool {
        let screenSize: CGRect = UIScreen.main.bounds
        return modelName == "Simulator" && screenSize.height == heigth
    }

}
Woeful answered 16/10, 2015 at 9:46 Comment(0)
U
5

This solution works for both physical devices and iOS simulator in a way that simulator returns the same model as physical device would return for a model e.g. "iPhone10,6" for iPhone X (GSM) rather than "x86_64".

Definition - Swift 4:

import UIKit

extension UIDevice {
    var modelName: String {
        var systemInfo = utsname()
        uname(&systemInfo)
        let machineMirror = Mirror(reflecting: systemInfo.machine)
        let identifier = machineMirror.children.reduce("") { identifier, element in
            guard let value = element.value as? Int8, value != 0 else { return identifier }
            return identifier + String(UnicodeScalar(UInt8(value)))
        }
        if let value = ProcessInfo.processInfo.environment["SIMULATOR_MODEL_IDENTIFIER"] {
            return value
        } else {
            return identifier
        }
    }
}

Usage:

print(UIDevice.current.modelName)
Unchartered answered 4/12, 2017 at 17:58 Comment(0)
I
4
#import <sys/utsname.h>

#define HARDWARE @{@"i386": @"Simulator",@"x86_64": @"Simulator",@"iPod1,1": @"iPod Touch",@"iPod2,1": @"iPod Touch 2nd Generation",@"iPod3,1": @"iPod Touch 3rd Generation",@"iPod4,1": @"iPod Touch 4th Generation",@"iPhone1,1": @"iPhone",@"iPhone1,2": @"iPhone 3G",@"iPhone2,1": @"iPhone 3GS",@"iPhone3,1": @"iPhone 4",@"iPhone4,1": @"iPhone 4S",@"iPhone5,1": @"iPhone 5",@"iPhone5,2": @"iPhone 5",@"iPhone5,3": @"iPhone 5c",@"iPhone5,4": @"iPhone 5c",@"iPhone6,1": @"iPhone 5s",@"iPhone6,2": @"iPhone 5s",@"iPad1,1": @"iPad",@"iPad2,1": @"iPad 2",@"iPad3,1": @"iPad 3rd Generation ",@"iPad3,4": @"iPad 4th Generation ",@"iPad2,5": @"iPad Mini",@"iPad4,4": @"iPad Mini 2nd Generation - Wifi",@"iPad4,5": @"iPad Mini 2nd Generation - Cellular",@"iPad4,1": @"iPad Air 5th Generation - Wifi",@"iPad4,2": @"iPad Air 5th Generation - Cellular"}

@interface ViewController ()
@end

@implementation ViewController

- (void)viewDidLoad
{
    [super viewDidLoad];
    struct utsname systemInfo;
    uname(&systemInfo);
    NSLog(@"hardware: %@",[HARDWARE objectForKey:[NSString stringWithCString: systemInfo.machine encoding:NSUTF8StringEncoding]]);
}
Illegality answered 28/8, 2014 at 5:9 Comment(0)
H
3

Below Function Perfectly Working on iOS7 or later version in Swift

func DeviceName()-> String {

        var myDeviceName : String = String()

        var systemInfo = [UInt8](count: sizeof(utsname), repeatedValue: 0)

        let model = systemInfo.withUnsafeMutableBufferPointer { (inout body: UnsafeMutableBufferPointer<UInt8>) -> String? in

            if uname(UnsafeMutablePointer(body.baseAddress)) != 0 {
                return nil
            }

            return String.fromCString(UnsafePointer(body.baseAddress.advancedBy(Int(_SYS_NAMELEN * 4))))
        }

        let deviceNamesByCode : [String: String] = ["iPod1,1":"iPod Touch 1",
                                                    "iPod2,1":"iPod Touch 2",
                                                    "iPod3,1":"iPod Touch 3",
                                                    "iPod4,1":"iPod Touch 4",
                                                    "iPod5,1":"iPod Touch 5",
                                                    "iPod7,1":"iPod Touch 6",
                                                    "iPhone1,1":"iPhone",
                                                    "iPhone1,2":"iPhone ",
                                                    "iPhone2,1":"iPhone ",
                                                    "iPhone3,1":"iPhone 4",
                                                    "iPhone3,2":"iPhone 4",
                                                    "iPhone3,3":"iPhone 4",
                                                    "iPhone4,1":"iPhone 4s",
                                                    "iPhone5,1":"iPhone 5",
                                                    "iPhone5,2":"iPhone 5",
                                                    "iPhone5,3":"iPhone 5c",
                                                    "iPhone5,4":"iPhone 5c",
                                                    "iPhone6,1":"iPhone 5s",
                                                    "iPhone6,2":"iPhone 5s",
                                                    "iPhone7,2":"iPhone 6",
                                                    "iPhone7,1":"iPhone 6 Plus",
                                                    "iPhone8,1":"iPhone 6s",
                                                    "iPhone8,2":"iPhone 6s Plus",
                                                    "iPhone8,4":"iPhone SE",
                                                    "iPad2,1":"iPad 2",
                                                    "iPad2,2":"iPad 2",
                                                    "iPad2,3":"iPad 2",
                                                    "iPad2,4":"iPad 2",
                                                    "iPad3,1":"iPad 3",
                                                    "iPad3,2":"iPad 3",
                                                    "iPad3,3":"iPad 3",
                                                    "iPad3,4":"iPad 4",
                                                    "iPad3,5":"iPad 4",
                                                    "iPad3,6":"iPad 4",
                                                    "iPad4,1":"iPad Air",
                                                    "iPad4,2":"iPad Air",
                                                    "iPad4,3":"iPad Air",
                                                    "iPad5,3":"iPad Air 2",
                                                    "iPad5,4":"iPad Air 2",
                                                    "iPad2,5":"iPad Mini",
                                                    "iPad2,6":"iPad Mini",
                                                    "iPad2,7":"iPad Mini",
                                                    "iPad4,4":"iPad Mini 2",
                                                    "iPad4,5":"iPad Mini 2",
                                                    "iPad4,6":"iPad Mini 2",
                                                    "iPad4,7":"iPad Mini 3",
                                                    "iPad4,8":"iPad Mini 3",
                                                    "iPad4,9":"iPad Mini 3",
                                                    "iPad5,1":"iPad Mini 4",
                                                    "iPad5,2":"iPad Mini 4",
                                                    "iPad6,3":"iPad Pro",
                                                    "iPad6,4":"iPad Pro",
                                                    "iPad6,7":"iPad Pro",
                                                    "iPad6,8":"iPad Pro",
                                                    "AppleTV5,3":"Apple TV",
                                                    "i386":"Simulator",
                                                    "x86_64":"Simulator"

        ]

        if model!.characters.count > 0 {
            myDeviceName = deviceNamesByCode[model!]!
        }else{
            myDeviceName = UIDevice.currentDevice().model
        }

        print("myDeviceName==\(myDeviceName)")
        return myDeviceName

    }
Hamulus answered 4/5, 2016 at 11:6 Comment(1)
Thanks for the update! And do please update for new devices too.Interest
E
3

Here’s a modern version of Aniruddh’s uname-based approach that doesn’t rely on Mirror and should work for Swift 4.2 and up:

import UIKit

extension UIDevice {
  var machineName: String {
    var info = utsname()
    return withUnsafeMutablePointer(to: &info) { info in
      // We could alternatively return nil here, or handle
      // errors some other way.
      guard uname(info) == 0 else { return model }
      let offset = MemoryLayout.offset(of: \utsname.machine)!
      let machine = UnsafeRawPointer(info).advanced(by: offset).assumingMemoryBound(to: CChar.self)
      return String(cString: machine)
    }
  }
}
Eunuchoidism answered 20/6, 2021 at 19:36 Comment(0)
E
3

It is possible to get the device name in Swift without using a Mirror. Swift can automatically convert things into pointers where needed. It's as simple as this:

/// Returns "iPhone1,1", etc.
var deviceName: String {
    var sysinfo = utsname()
    uname(&sysinfo)
    return String(cString: &sysinfo.machine.0)
}

(Hat-tip to this underrated answer https://mcmap.net/q/44868/-how-to-determine-the-current-iphone-device-model)

Eaddy answered 26/8, 2021 at 16:40 Comment(4)
generates a deprecation warning nowadays: 'init(cString:)' is deprecated: Use String(_ scalar: Unicode.Scalar)Ho
After running it I got the error: Fatal error: input of String.init(cString:) must be null-terminatedHo
a revised answer is available at stackoverflow.com/a/73232453Casuist
Warning, the code crashes: Thread 1: Fatal error: input of String.init(cString:) must be null-terminatedGorgias
I
3

Although this question was asked in 2012, Apple still doesn't give a way to convert a device modal identifier to the device name. There have been a lot of answers which rely on hardcoding these names which unfortunately quickly goes out of date when Apple release new devices.

What we need is a way to get a constantly updated list and that exists here: https://github.com/ptrkstr/Devices

Every time new devices get added, this Swift package will update and all you need to do is update your dependency to get them.

Inexact answered 26/4, 2022 at 5:25 Comment(0)
D
2
//
//  UIDevice+Hardware.h
//  gauravds
//

#import <UIKit/UIKit.h>

@interface UIDevice (Hardware)

- (NSString *)modelIdentifier;
- (NSString *)modelName;

@end

Why not create a category. Don't use malloc method security leak issue. Use safe functions.

NSLog(@"%@ %@", [[UIDevice currentDevice] modelName], [[UIDevice currentDevice] modelIdentifier]);

See the implentations

//
//  UIDevice+Hardware.m
//  gauravds
//

#import "UIDevice+Hardware.h"
#import <sys/utsname.h>

@implementation UIDevice (Hardware)

- (NSString *)modelIdentifier {
    struct utsname systemInfo;
    uname(&systemInfo);
    return [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
}

- (NSString *)modelName {
    return [self modelNameForModelIdentifier:[self modelIdentifier]];
}

- (NSString *)modelNameForModelIdentifier:(NSString *)modelIdentifier {
    // iPhone http://theiphonewiki.com/wiki/IPhone

    if ([modelIdentifier isEqualToString:@"iPhone1,1"])    return @"iPhone 1G";
    if ([modelIdentifier isEqualToString:@"iPhone1,2"])    return @"iPhone 3G";
    if ([modelIdentifier isEqualToString:@"iPhone2,1"])    return @"iPhone 3GS";
    if ([modelIdentifier isEqualToString:@"iPhone3,1"])    return @"iPhone 4 (GSM)";
    if ([modelIdentifier isEqualToString:@"iPhone3,2"])    return @"iPhone 4 (GSM Rev A)";
    if ([modelIdentifier isEqualToString:@"iPhone3,3"])    return @"iPhone 4 (CDMA)";
    if ([modelIdentifier isEqualToString:@"iPhone4,1"])    return @"iPhone 4S";
    if ([modelIdentifier isEqualToString:@"iPhone5,1"])    return @"iPhone 5 (GSM)";
    if ([modelIdentifier isEqualToString:@"iPhone5,2"])    return @"iPhone 5 (Global)";
    if ([modelIdentifier isEqualToString:@"iPhone5,3"])    return @"iPhone 5c (GSM)";
    if ([modelIdentifier isEqualToString:@"iPhone5,4"])    return @"iPhone 5c (Global)";
    if ([modelIdentifier isEqualToString:@"iPhone6,1"])    return @"iPhone 5s (GSM)";
    if ([modelIdentifier isEqualToString:@"iPhone6,2"])    return @"iPhone 5s (Global)";
    if ([modelIdentifier isEqualToString:@"iPhone7,1"])    return @"iPhone 6 Plus";
    if ([modelIdentifier isEqualToString:@"iPhone7,2"])    return @"iPhone 6";
    if ([modelIdentifier isEqualToString:@"iPhone8,1"])    return @"iPhone 6s";
    if ([modelIdentifier isEqualToString:@"iPhone8,2"])    return @"iPhone 6s Plus";
    if ([modelIdentifier isEqualToString:@"iPhone8,4"])    return @"iPhone SE";
    if ([modelIdentifier isEqualToString:@"iPhone9,1"])    return @"iPhone 7";
    if ([modelIdentifier isEqualToString:@"iPhone9,2"])    return @"iPhone 7 Plus";
    if ([modelIdentifier isEqualToString:@"iPhone9,3"])    return @"iPhone 7";
    if ([modelIdentifier isEqualToString:@"iPhone9,4"])    return @"iPhone 7 Plus";
    if ([modelIdentifier isEqualToString:@"iPhone10,1"])   return @"iPhone 8";          // US (Verizon), China, Japan
    if ([modelIdentifier isEqualToString:@"iPhone10,2"])   return @"iPhone 8 Plus";     // US (Verizon), China, Japan
    if ([modelIdentifier isEqualToString:@"iPhone10,3"])   return @"iPhone X";          // US (Verizon), China, Japan
    if ([modelIdentifier isEqualToString:@"iPhone10,4"])   return @"iPhone 8";          // AT&T, Global
    if ([modelIdentifier isEqualToString:@"iPhone10,5"])   return @"iPhone 8 Plus";     // AT&T, Global
    if ([modelIdentifier isEqualToString:@"iPhone10,6"])   return @"iPhone X";          // AT&T, Global

    // iPad http://theiphonewiki.com/wiki/IPad

    if ([modelIdentifier isEqualToString:@"iPad1,1"])      return @"iPad 1G";
    if ([modelIdentifier isEqualToString:@"iPad2,1"])      return @"iPad 2 (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad2,2"])      return @"iPad 2 (GSM)";
    if ([modelIdentifier isEqualToString:@"iPad2,3"])      return @"iPad 2 (CDMA)";
    if ([modelIdentifier isEqualToString:@"iPad2,4"])      return @"iPad 2 (Rev A)";
    if ([modelIdentifier isEqualToString:@"iPad3,1"])      return @"iPad 3 (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad3,2"])      return @"iPad 3 (GSM)";
    if ([modelIdentifier isEqualToString:@"iPad3,3"])      return @"iPad 3 (Global)";
    if ([modelIdentifier isEqualToString:@"iPad3,4"])      return @"iPad 4 (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad3,5"])      return @"iPad 4 (GSM)";
    if ([modelIdentifier isEqualToString:@"iPad3,6"])      return @"iPad 4 (Global)";
    if ([modelIdentifier isEqualToString:@"iPad6,11"])     return @"iPad (5th gen) (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad6,12"])     return @"iPad (5th gen) (Cellular)";

    if ([modelIdentifier isEqualToString:@"iPad4,1"])      return @"iPad Air (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad4,2"])      return @"iPad Air (Cellular)";
    if ([modelIdentifier isEqualToString:@"iPad5,3"])      return @"iPad Air 2 (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad5,4"])      return @"iPad Air 2 (Cellular)";

    // iPad Mini http://theiphonewiki.com/wiki/IPad_mini

    if ([modelIdentifier isEqualToString:@"iPad2,5"])      return @"iPad mini 1G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad2,6"])      return @"iPad mini 1G (GSM)";
    if ([modelIdentifier isEqualToString:@"iPad2,7"])      return @"iPad mini 1G (Global)";
    if ([modelIdentifier isEqualToString:@"iPad4,4"])      return @"iPad mini 2G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad4,5"])      return @"iPad mini 2G (Cellular)";
    if ([modelIdentifier isEqualToString:@"iPad4,6"])      return @"iPad mini 2G (Cellular)"; // TD-LTE model see https://support.apple.com/en-us/HT201471#iPad-mini2
    if ([modelIdentifier isEqualToString:@"iPad4,7"])      return @"iPad mini 3G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad4,8"])      return @"iPad mini 3G (Cellular)";
    if ([modelIdentifier isEqualToString:@"iPad4,9"])      return @"iPad mini 3G (Cellular)";
    if ([modelIdentifier isEqualToString:@"iPad5,1"])      return @"iPad mini 4G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad5,2"])      return @"iPad mini 4G (Cellular)";

    // iPad Pro https://www.theiphonewiki.com/wiki/IPad_Pro

    if ([modelIdentifier isEqualToString:@"iPad6,3"])      return @"iPad Pro (9.7 inch) 1G (Wi-Fi)"; // http://pdadb.net/index.php?m=specs&id=9938&c=apple_ipad_pro_9.7-inch_a1673_wifi_32gb_apple_ipad_6,3
    if ([modelIdentifier isEqualToString:@"iPad6,4"])      return @"iPad Pro (9.7 inch) 1G (Cellular)"; // http://pdadb.net/index.php?m=specs&id=9981&c=apple_ipad_pro_9.7-inch_a1675_td-lte_32gb_apple_ipad_6,4
    if ([modelIdentifier isEqualToString:@"iPad6,7"])      return @"iPad Pro (12.9 inch) 1G (Wi-Fi)"; // http://pdadb.net/index.php?m=specs&id=8960&c=apple_ipad_pro_wifi_a1584_128gb
    if ([modelIdentifier isEqualToString:@"iPad6,8"])      return @"iPad Pro (12.9 inch) 1G (Cellular)"; // http://pdadb.net/index.php?m=specs&id=8965&c=apple_ipad_pro_td-lte_a1652_32gb_apple_ipad_6,8
    if ([modelIdentifier isEqualToString:@"iPad 7,1"])     return @"iPad Pro (12.9 inch) 2G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad 7,2"])     return @"iPad Pro (12.9 inch) 2G (Cellular)";
    if ([modelIdentifier isEqualToString:@"iPad 7,3"])     return @"iPad Pro (10.5 inch) 1G (Wi-Fi)";
    if ([modelIdentifier isEqualToString:@"iPad 7,4"])     return @"iPad Pro (10.5 inch) 1G (Cellular)";

    // iPod http://theiphonewiki.com/wiki/IPod

    if ([modelIdentifier isEqualToString:@"iPod1,1"])      return @"iPod touch 1G";
    if ([modelIdentifier isEqualToString:@"iPod2,1"])      return @"iPod touch 2G";
    if ([modelIdentifier isEqualToString:@"iPod3,1"])      return @"iPod touch 3G";
    if ([modelIdentifier isEqualToString:@"iPod4,1"])      return @"iPod touch 4G";
    if ([modelIdentifier isEqualToString:@"iPod5,1"])      return @"iPod touch 5G";
    if ([modelIdentifier isEqualToString:@"iPod7,1"])      return @"iPod touch 6G"; // as 6,1 was never released 7,1 is actually 6th generation

    // Apple TV https://www.theiphonewiki.com/wiki/Apple_TV

    if ([modelIdentifier isEqualToString:@"AppleTV1,1"])      return @"Apple TV 1G";
    if ([modelIdentifier isEqualToString:@"AppleTV2,1"])      return @"Apple TV 2G";
    if ([modelIdentifier isEqualToString:@"AppleTV3,1"])      return @"Apple TV 3G";
    if ([modelIdentifier isEqualToString:@"AppleTV3,2"])      return @"Apple TV 3G"; // small, incremental update over 3,1
    if ([modelIdentifier isEqualToString:@"AppleTV5,3"])      return @"Apple TV 4G"; // as 4,1 was never released, 5,1 is actually 4th generation

    // Simulator
    if ([modelIdentifier hasSuffix:@"86"] || [modelIdentifier isEqual:@"x86_64"])
    {
        BOOL smallerScreen = ([[UIScreen mainScreen] bounds].size.width < 768.0);
        return (smallerScreen ? @"iPhone Simulator" : @"iPad Simulator");
    }

    return modelIdentifier;
}

@end
Directions answered 11/5, 2018 at 6:42 Comment(0)
F
2

Swift 4 or later

extension UIDevice {
    var modelName: String {
        if let modelName = ProcessInfo.processInfo.environment["SIMULATOR_MODEL_IDENTIFIER"] { return modelName }
        var info = utsname()
        uname(&info)
        return String(String.UnicodeScalarView(
                   Mirror(reflecting: info.machine)
                    .children
                    .compactMap {
                        guard let value = $0.value as? Int8 else { return nil }
                        let unicode = UnicodeScalar(UInt8(value))
                        return unicode.isASCII ? unicode : nil
                    }))
    }
}

UIDevice.current.modelName   // "iPad6,4"
Forgather answered 4/9, 2018 at 23:6 Comment(1)
It can be much simpler, ProcessInfo.processInfo.environment["SIMULATOR_DEVICE_NAME"] is enough.Shrift
R
1

For save time of others. Because accepted, must voted answer propose library that uses private API and my app was rejected because of uidevice-extension just yesterday! I am switching to GBDeviceInfo library, installed as pod as well, for now it looks nice, maintained and updated to latest devices.

Rayshell answered 3/8, 2018 at 16:34 Comment(0)
P
0

If you have a plist of devices (eg maintained by @Tib above in https://mcmap.net/q/44892/-how-to-get-device-make-and-model-on-ios) to handle it if Swift 3 you'd use:

extension UIDevice {
    /// Fetches the information about the name of the device.
    ///
    /// - Returns: Should return meaningful device name, if not found will return device system code.
    public static func modelName() -> String {
        let physicalName = deviceSystemCode()
        if let deviceTypes = deviceTypes(), let modelName = deviceTypes[physicalName] as? String {
            return modelName
        }
        return physicalName
    }
}

private extension UIDevice {
    /// Fetches from system the code of the device
    static func deviceSystemCode() -> String {
        var systemInfo = utsname()
        uname(&systemInfo)
        let machineMirror = Mirror(reflecting: systemInfo.machine)
        let identifier = machineMirror.children.reduce("") { identifier, element in
            guard let value = element.value as? Int8, value != 0 else { return identifier }
            return identifier + String(UnicodeScalar(UInt8(value)))
        }
        return identifier
    }

    /// Fetches the plist entries from plist maintained in https://mcmap.net/q/44892/-how-to-get-device-make-and-model-on-ios
    ///
    /// - Returns: A dictionary with pairs of deviceSystemCode <-> meaningfulDeviceName.
    static func deviceTypes() -> NSDictionary? {
        if let fileUrl = Bundle.main.url(forResource: "your plist name", withExtension: "plist"),
            let configurationDictionary = NSDictionary(contentsOf: fileUrl) {
            return configurationDictionary
        }
        return nil
    }
}

Later you can call it using UIDevice.modelName().

Additional credits go to @Tib (for plist), @Aniruddh Joshi (for deviceSystemCode() function).

Parsec answered 15/11, 2017 at 14:12 Comment(0)
F
0

What about using ideviceinfo to get these values? Should be able to install it using brew install ideviceinfo

Then run:

PRODUCT_NAME=$(ideviceinfo --udid $DEVICE_UDID --key ProductName)
PRODUCT_TYPE=$(ideviceinfo --udid $DEVICE_UDID --key ProductType)
PRODUCT_VERSION=$(ideviceinfo --udid $DEVICE_UDID --key ProductVersion)
Furthermore answered 6/3, 2019 at 17:30 Comment(0)
Y
0

For anyone not wanting to use Swift's Mirror, here's a solution using normal types (with support for simulators too):

#if targetEnvironment(simulator)
@objc public protocol UIDevicePrivate {
    @objc func _deviceInfoForKey(_:String) -> Any?
}
#endif

extension UIDevice {
    var hardwareModel: String {
#if targetEnvironment(simulator)
        let privateSelf = unsafeBitCast(self, to:UIDevicePrivate.self)
        if let model = privateSelf._deviceInfoForKey("HWModelStr") as? String {
            return model + " (Simulator)"
        }
#endif
        var systemInfo = utsname()
        uname(&systemInfo)
        return String(characters: systemInfo.machine)
    }
}

typealias StaticArray256<Element> = (Element, Element, Element,Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element, Element)

// This function is necessary because Swift really doesn't like creating a 256 element long static array

func enumerate<T>(tuple: StaticArray256<T>, body: (Int, T) -> Void) {
    body(0, tuple.0)
    body(1, tuple.1)
    body(2, tuple.2)
    body(3, tuple.3)
    body(4, tuple.4)
    body(5, tuple.5)
    body(6, tuple.6)
    body(7, tuple.7)
    body(8, tuple.8)
    body(9, tuple.9)
    body(10, tuple.10)
    body(11, tuple.11)
    body(12, tuple.12)
    body(13, tuple.13)
    body(14, tuple.14)
    body(15, tuple.15)
    body(16, tuple.16)
    body(17, tuple.17)
    body(18, tuple.18)
    body(19, tuple.19)
    body(20, tuple.20)
    body(21, tuple.21)
    body(22, tuple.22)
    body(23, tuple.23)
    body(24, tuple.24)
    body(25, tuple.25)
    body(26, tuple.26)
    body(27, tuple.27)
    body(28, tuple.28)
    body(29, tuple.29)
    body(30, tuple.30)
    body(31, tuple.31)
    body(32, tuple.32)
    body(33, tuple.33)
    body(34, tuple.34)
    body(35, tuple.35)
    body(36, tuple.36)
    body(37, tuple.37)
    body(38, tuple.38)
    body(39, tuple.39)
    body(40, tuple.40)
    body(41, tuple.41)
    body(42, tuple.42)
    body(43, tuple.43)
    body(44, tuple.44)
    body(45, tuple.45)
    body(46, tuple.46)
    body(47, tuple.47)
    body(48, tuple.48)
    body(49, tuple.49)
    body(50, tuple.50)
    body(51, tuple.51)
    body(52, tuple.52)
    body(53, tuple.53)
    body(54, tuple.54)
    body(55, tuple.55)
    body(56, tuple.56)
    body(57, tuple.57)
    body(58, tuple.58)
    body(59, tuple.59)
    body(60, tuple.60)
    body(61, tuple.61)
    body(62, tuple.62)
    body(63, tuple.63)
    body(64, tuple.64)
    body(65, tuple.65)
    body(66, tuple.66)
    body(67, tuple.67)
    body(68, tuple.68)
    body(69, tuple.69)
    body(70, tuple.70)
    body(71, tuple.71)
    body(72, tuple.72)
    body(73, tuple.73)
    body(74, tuple.74)
    body(75, tuple.75)
    body(76, tuple.76)
    body(77, tuple.77)
    body(78, tuple.78)
    body(79, tuple.79)
    body(80, tuple.80)
    body(81, tuple.81)
    body(82, tuple.82)
    body(83, tuple.83)
    body(84, tuple.84)
    body(85, tuple.85)
    body(86, tuple.86)
    body(87, tuple.87)
    body(88, tuple.88)
    body(89, tuple.89)
    body(90, tuple.90)
    body(91, tuple.91)
    body(92, tuple.92)
    body(93, tuple.93)
    body(94, tuple.94)
    body(95, tuple.95)
    body(96, tuple.96)
    body(97, tuple.97)
    body(98, tuple.98)
    body(99, tuple.99)
    body(100, tuple.100)
    body(101, tuple.101)
    body(102, tuple.102)
    body(103, tuple.103)
    body(104, tuple.104)
    body(105, tuple.105)
    body(106, tuple.106)
    body(107, tuple.107)
    body(108, tuple.108)
    body(109, tuple.109)
    body(110, tuple.110)
    body(111, tuple.111)
    body(112, tuple.112)
    body(113, tuple.113)
    body(114, tuple.114)
    body(115, tuple.115)
    body(116, tuple.116)
    body(117, tuple.117)
    body(118, tuple.118)
    body(119, tuple.119)
    body(120, tuple.120)
    body(121, tuple.121)
    body(122, tuple.122)
    body(123, tuple.123)
    body(124, tuple.124)
    body(125, tuple.125)
    body(126, tuple.126)
    body(127, tuple.127)
    body(128, tuple.128)
    body(129, tuple.129)
    body(130, tuple.130)
    body(131, tuple.131)
    body(132, tuple.132)
    body(133, tuple.133)
    body(134, tuple.134)
    body(135, tuple.135)
    body(136, tuple.136)
    body(137, tuple.137)
    body(138, tuple.138)
    body(139, tuple.139)
    body(140, tuple.140)
    body(141, tuple.141)
    body(142, tuple.142)
    body(143, tuple.143)
    body(144, tuple.144)
    body(145, tuple.145)
    body(146, tuple.146)
    body(147, tuple.147)
    body(148, tuple.148)
    body(149, tuple.149)
    body(150, tuple.150)
    body(151, tuple.151)
    body(152, tuple.152)
    body(153, tuple.153)
    body(154, tuple.154)
    body(155, tuple.155)
    body(156, tuple.156)
    body(157, tuple.157)
    body(158, tuple.158)
    body(159, tuple.159)
    body(160, tuple.160)
    body(161, tuple.161)
    body(162, tuple.162)
    body(163, tuple.163)
    body(164, tuple.164)
    body(165, tuple.165)
    body(166, tuple.166)
    body(167, tuple.167)
    body(168, tuple.168)
    body(169, tuple.169)
    body(170, tuple.170)
    body(171, tuple.171)
    body(172, tuple.172)
    body(173, tuple.173)
    body(174, tuple.174)
    body(175, tuple.175)
    body(176, tuple.176)
    body(177, tuple.177)
    body(178, tuple.178)
    body(179, tuple.179)
    body(180, tuple.180)
    body(181, tuple.181)
    body(182, tuple.182)
    body(183, tuple.183)
    body(184, tuple.184)
    body(185, tuple.185)
    body(186, tuple.186)
    body(187, tuple.187)
    body(188, tuple.188)
    body(189, tuple.189)
    body(190, tuple.190)
    body(191, tuple.191)
    body(192, tuple.192)
    body(193, tuple.193)
    body(194, tuple.194)
    body(195, tuple.195)
    body(196, tuple.196)
    body(197, tuple.197)
    body(198, tuple.198)
    body(199, tuple.199)
    body(200, tuple.200)
    body(201, tuple.201)
    body(202, tuple.202)
    body(203, tuple.203)
    body(204, tuple.204)
    body(205, tuple.205)
    body(206, tuple.206)
    body(207, tuple.207)
    body(208, tuple.208)
    body(209, tuple.209)
    body(210, tuple.210)
    body(211, tuple.211)
    body(212, tuple.212)
    body(213, tuple.213)
    body(214, tuple.214)
    body(215, tuple.215)
    body(216, tuple.216)
    body(217, tuple.217)
    body(218, tuple.218)
    body(219, tuple.219)
    body(220, tuple.220)
    body(221, tuple.221)
    body(222, tuple.222)
    body(223, tuple.223)
    body(224, tuple.224)
    body(225, tuple.225)
    body(226, tuple.226)
    body(227, tuple.227)
    body(228, tuple.228)
    body(229, tuple.229)
    body(230, tuple.230)
    body(231, tuple.231)
    body(232, tuple.232)
    body(233, tuple.233)
    body(234, tuple.234)
    body(235, tuple.235)
    body(236, tuple.236)
    body(237, tuple.237)
    body(238, tuple.238)
    body(239, tuple.239)
    body(240, tuple.240)
    body(241, tuple.241)
    body(242, tuple.242)
    body(243, tuple.243)
    body(244, tuple.244)
    body(245, tuple.245)
    body(246, tuple.246)
    body(247, tuple.247)
    body(248, tuple.248)
    body(249, tuple.249)
    body(250, tuple.250)
    body(251, tuple.251)
    body(252, tuple.252)
    body(253, tuple.253)
    body(254, tuple.254)
    body(255, tuple.255)
}

extension Array {
    init(staticArray: StaticArray256<Element>) {
        var array = [Element]()
        enumerate(tuple: staticArray) { array.append($1) }
        self = array
    }
}

extension String {
    init(characters: StaticArray256<CChar>) {
        self.init(String.UnicodeScalarView(Array(staticArray: characters).compactMap(Int.init).filter({ $0 > 0 }).compactMap(UnicodeScalar.init)))
    }
}
Yusuk answered 26/8, 2022 at 18:42 Comment(0)
S
-5

Kotlin Native:

memScoped {
            val q = alloc<utsname>()
            uname(q.ptr)
            val identifier = NSString.stringWithCString(q.machine, encoding = NSUTF8StringEncoding)
        }
Snakeroot answered 13/8, 2020 at 16:1 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.