I tried to use the float16_t type in my iOS app to save memory space. It seems to work perfectly on device, but it does not build on simulator.
In the simulator build it fails with
Unknown type name 'float16_t'; did you mean 'float_t'?
The float16_t seems to be defined in arm_neon.h.
Can this be fixed so that I can use that type on simulator?
Very obvious!
float16_t is declared in "arm_neon.h" means the type is strictly for ARM based CPU instructions (specifically ARM CPUs with supported NEON instruction set).
Till date, all iOS devices run on ARM based CPU. So your code is good when compiled for device (Though, possibly won't run in some very old iOS device with older ARM cpus without NEON).
However, iOS Simulator runs on a Mac, which is built on top of x86/x64 CPU architecture, not ARM. So ARM types simply don't work here.
I'm not sure why you do really want to work with some ARM NEON optimized data types like float16_t, when float_t works great, everywhere. But if you still want to use it and want your app to run everywhere, you should use conditional compilation directives to compile your code:
#if TARGET_IPHONE_SIMULATOR
float_t x;
#else
float16_t x;
#endif
Hope it helps.
Related
With bitcode, Apple say they can re-build my application on demand, whenever they think it is necessary.
If my source code contains preprocessor macros, when will those run?
When I build and archive my IPA locally? Or also when Apple re-builds the app?
I'm considering both custom macros, as well as built-in ones such as __DATE__ and __TIME__. Which date/time will it get if Apple re-builds the app in the app store?
No; Apple will have a 32 bit version and a 64 bit version for your app in bit code; that's all. All the #define's will be evaluated by your compiler and not be sent to Apple.
With what they have Apple can easily produce a new version of your app that will run on new versions of the ARM processor. They most likely could build a new version that would run on an Intel processor instead of an ARM processor (while their instruction set and implementation are very different, how these chips behave is actually very similar). Building a version for a little-endian PowerPC would be possible; a version for big-endian PowerPC would quite likely not work if your app includes code that needed to be different on a big-endian processor.
__DATE__ and __TIME__ would be the ones that were valid when you built the app.
The result of Apple building a new version for a new processor from bitcode should be exactly the same as if you had submitted the app with code for that processor. Obviously you don't have a compiler for ARM13 which will be introduced in 2022, but if Apple builds that version from your submitted bit code, it should be as if you had had that compiler today.
I did find the 64 Bit Transition Guide for Cocoa Touch but to be honest, I find it to be very confusing. I use primarily CGFloat and int in my code, and in Core Data my integers are 64-bit. My app compiles and runs fine in the simulator for 64 bit, and on my iPhone 5, but I do not have a 5s to test with, so I cannot be sure. For example, what does it mean to "Fix alignment issues caused by changes in data type sizes." Is there something different that we need to do with pointers, which seem to have different sizes in 32 bit and 64 bit apps?
EDIT: I just changed my architectures to include 64-bit and it gave me a whole slew of errors, so that is a very helpful place to start.
EDIT2:This Link was actually a little more helpful than the one I had originally found.
The easiest is to run the App on a Simulator that includes 64bit. Use iPad Air or iPhone6, or "Archive" the App. This will automatically show the warnings. The Simulators (iPad Air or iPhone6) will reliably reproduce 64bit problems.
However, I had about 100 warnings and one real problem. Casting a int to BOOL works differently in 64 bit. BOOL b=(BOOL)3; b==YES is FALSE in 32bit but TRUE in 64bit.
Another special case is NSNotFound, a value different on 32bit and 64bit! Look for Comparison of constant 'NSNotFound' (9223372036854775807) with expression of type 'int' is always false among the warnings.
In the end its about changing or casting tons of list counts (that never could hold long valued amount of objects anyway) in for loops. Useless work, IMO. Apple seems to want to save space on the devices by not including 32bit libs on 64bit platforms, or stripping apps?
I need to compute MSB (most significant bit) on millions of 32-bit integers on iPad very fast. I have my own (ugly) implementation of MSB written on plain C, which is slow. ARM processors have CLZ (count leading zeroes) hardware command, which can be very useful for that. According to ARM reference there is an intrinsic C function __CLZ. How can I add support of ARM intrinsic functions to my Xcode project?
P.S. I've managed to find the way of accessing hardware CLZ from NEON (by including arm_neon.h), but that's not what I need, because it's only works with vector, but I need scalar MSB.
I found ARM intrinsic functions names on page 44 of ARM C language extensions. Some of them works in Xcode. This prints 31, as expected:
NSLog(#"%u", __builtin_clz(1));
Notes:
I haven't found any references of this in Apple docs. Most likely Xcode inherited those functions from LLVM or CLANG.
You don't need to include any special headers or frameworks to use those functions. Xcode IDE autocomplete doesn't know about them.
Only a few functions from extensions list are implemented. According to pages 12-13 of the same document it should be two header files: arm_acle.h for non-NEON intrinsics and arm_neon.h for NEON intrinsics. Xcode have only the second file, but some of the functions from the first file declared somewhere else.
This may be obvious, but if if you use ARM-specific instructions, you will not be able to run your app in the iOS simulator. The simulator uses the native x86-64 hardware of your Mac.
You could create a wrapper function that uses a compiler directive to use the ARM command or fall back to the "ugly" code if you don't have support.
Some of my code reference a library which use arm_neon.h; when I tried to compile using "Simulator", I received a bunch of errors.
I am using LLVM 4.2 compiler, what should I do to get it compiled with arm neon?
You can't compile ARM NEON code for the simulator because the simulator doesn't execute ARM machine code, it executes i386 machine code. See here for more info, but here is a snippet:
Don’t forget that you’ll need to disable the NEON code at compile time when building for the simulator, as your application is compiled for x86 when targeting the simulator, and NEON code will cause build errors in this context. This means you always need to also write a generic C version of the algorithm, even if you only target the iPad, or you won’t be able to run your application in the simulator.
So it's fairly easy to figure out what kind of CPU an iOS device runs by querying sysctlbyname("hw.cpusubtype", ...), but there seems to be no obvious way to figure out what features the CPU actually has (think VFP, NEON, Thumb, ...). Can someone think of a way to do this?
Basically, what I need is something similar to getauxval(AT_HWCAP) on Linux/Android, which returns a bit mask of features supported by the CPU.
A few things to note:
The information must be retrieved at runtime from the OS. No preprocessor defines.
Fat binaries is not a solution. I really do need to know this stuff in an ARM v6 binary.
Thanks in advance!
sysctlbyname has “hw.optional.neon”. I do not see a name for VFP, except “hw.optional.vfp_shortvector”, which is a deprecated feature.
Do a matrix float multiplaction via accelerate.framework and measure the execution time. The difference will be huge enough between Neon and VFP driven math, you simply cannot miss.
Thumb is always there, and the presence of NEON means armv7= Thumb2.
First, consider carefully whether or not you really need to support armv6 binaries for iOS. According to published version share statistics, something like 98.5% of iOS devices are running iOS 5.0 or later, which does not support armv6 devices (armv6 binaries will still run on current iOS versions, obviously, but all new apps should really be targeting armv7; there’s basically zero reason for your customers to be shipping armv6 binaries for iOS today).
Similarly, your concerns about code size are misplaced. If you provide a fat library, and your customer builds an armv6 binary against it, only the armv6 bits of your library will be built into their application. Furthermore, code size is usually a nearly trivial fraction of application bundle size; most of the size of an application comes from other resources.
Ok. All that aside, if you really want to pursue this: VFP and thumb are supported on all iOS devices, so there’s no need to check for support. You can check for NEON and thumb-2 using the method that Eric Postpischil suggested (all armv7 iOS devices have NEON support, so availability of NEON coincides exactly with availability of thumb-2).