Related
tl;dr: I get this error message:
ld: -alias_list and -bitcode_bundle (Xcode setting ENABLE_BITCODE=YES)
cannot be used together
How do I fix it?
I am trying to create my own version of a third-party library. I want to make sure that none of my calls are going to the system version of this library, so I use --alias-list to put a prefix on all the symbols, and generate a header file which renames all the symbols from foo to MJB_foo. My build system then includes this header file with the --include option whenever I want to use this library.
This works great on Android and Linux (and I'm pretty sure it will eventually work on Windows too). However I get the above error when I try to link the shared library. How do I achieve the same effect?
In Build Settings of project you need to set Enable Bitcode to No. For iOS Apps bitcode is default but optional so you can send the app to AppStore without bitcode.
Bitcode re-optimize your app binary in the future without the need to submit a new version of your app to the App Store.
From Apple Doc:
For iOS apps, bitcode is the default, but optional. For watchOS and tvOS apps, bitcode is required. If you provide bitcode, all apps and frameworks in the app bundle (all targets in the project) need to include bitcode.
https://help.apple.com/xcode/mac/current/#/devbbdc5ce4f
What I have ended up doing is forcing the inclusion of the header full of #defines when building the library, as well as when using it. This allows me to drop --alias-list from the linker command line, so it is happy.
Sadly, this is not the complete solution. The library (it is OpenSSL) has a number of assembler modules, so those have to be patched with sed by the build script first.
It also has some macros which turn
FOO(SHA1)
into
void SHA1_Init(struct SHA1_CTX *ctx)
the problem is that SHA1 is one of the functions I am renaming, so it becomes instead:
void MJB_SHA1_Init(struct MJB_SHA1_CTX *ctx)
renaming the function is harmless (because it turns out it gets renamed uniformly), but I am not renaming the structs. The solution is to create another small file which renames MJB_SHA1_CTX et al back to SHA1_CTX.
*When bitcode is enabled for a target, all the objects, static libraries and user frameworks used when linking that target must contain bitcode.
Otherwise, an error or a warning will be issued by the linker. (Note: missing bitcode is currently a warning for iOS, but it will become an error in an upcoming release of Xcode .)
ENABLE_BITCODE should be consistently turned on for all the targets. If you use a library or framework provided by a third party, please contact the vendor for an updated version which contains bitcode."
This was simply an update that didn't change anything to do with the rejection reason. Here is the response from the resolution center:
Reasons
Program License Agreement
PLA 3.3.12
We found your app uses the iOS Advertising Identifier but does not include ad functionality. This does not comply with the terms of the iOS Developer Program License Agreement, as required by the App Store Review Guidelines.
Specifically, section 3.3.12 of the iOS Developer Program License Agreement states:
"You and Your Applications (and any third party with whom you have contracted to serve advertising) may use the Advertising Identifier, and any information obtained through the use of the Advertising Identifier, only for the purpose of serving advertising. If a user resets the Advertising Identifier, then You agree not to combine, correlate, link or otherwise associate, either directly or indirectly, the prior Advertising Identifier and any derived information with the reset Advertising Identifier."
Please check your code - including any third-party libraries - to remove any instances of:
class: ASIdentifierManager
selector: advertisingIdentifier
framework: AdSupport.framework
If you are planning to incorporate ads in a future version, please remove the Advertising Identifier from your app until you have included ad functionality.
To help locate the Advertising Identifier, use the “nm” tool. For information on the “nm” tool, open a terminal window and enter, “man nm.”
If you do not have access to the libraries source, you may be able to search the compiled binary using the "strings" or "otool" command line tools. The "strings" tool lists the methods that the library calls, and "otool -ov" will list the Objective-C class structures and their defined methods. These techniques can help you narrow down where the problematic code resides.
The third party libraries I'm using is the latest version of parse.com sdk, latest version of flurry analytics, and version 2.2 of test flight. Does anybody know which library is the issue? Thanks
In Terminal:
Go to the root folder of your project
Type: grep -r advertisingIdentifier . (the dot at the end is critical)
This will recursively check every file, and give you the name of the offending library.
(in my case, it was Flurry)
Update
Google released Google Analytics Services iOS SDK v3.03c which removes the AdSupport.framework dependency by default.
Full changelog entry for Release Version 3.03c (February 19, 2014): https://developers.google.com/analytics/devguides/collection/ios/changelog
Old Awnser
My problem was with Google Analytics and TestFlight.
For TestFlight I just update the library to the version 2.2.1 (https://www.testflightapp.com/sdk/ios/release_notes/2.2.1/).
But for updating Google Analytics I had to remove the -ObjC flag. But as I use Cocoapods to manage some of third libraries, I couldn't just remove it. So I did the follow:
1 - started updating the libGoogleAnalytics.a to Version 3.03a (February 5, 2014)
2 - then a removed also the AdSupport.framework
3 - added "-force_load\ "${PROJECT_DIR}/Source/Library/GoogleAnalyticsServicesiOS_3.03a"" under "Target --> Build Settings --> Other Linker Flags"
(Note that in my project the GoogleAnalytics is inside /Source/Library/ folder, and you have to configure your own)
But as I coudn't remove -ObjC flag I searched for how to use -force_load flag with Cocoapods, then I found two useful links:
1 - https://github.com/CocoaPods/CocoaPods/issues/712
2 - http://www.deanmao.com/2012/12/31/linker-error-using-cocoapods/
To summarize I changed the -ObjC flag for "-force_load $(TARGET_BUILD_DIR)/libPods.a" also under "Target --> Build Settings --> Other Linker Flags"
But again, when I tried to publish my app I got an error telling me that the compiler didn't find libPods.a, so I went to "Target --> Build Settings --> Other Linker Flags --> Release" and change this string $(TARGET_BUILD_DIR) to ${BUILT_PRODUCTS_DIR}.
So my Other Linker Flags became like the image below.
Hope to help somebody.
Sorry for my english.
=]
For me, Flurry Analytics and TestFlight were both the problem.
For TestFlight, it's as easy as updating it. The 2.2.1 version won't cause any problem (I checked using strings, as Apple suggest)
For Flurry, there is currently no fix apart from removing Flurry, and contrary to Lou Weed suggestion, even if AdSupport.framework is not linked, your app will be rejected.
Here is Flurry support answer :
"Thank you for reaching out to Flurry. We have recently learned that Apple has rejected some apps it believes are using the Identifier for Advertising (IDFA) without including ad functionality. Please note that Flurry does not collect the IDFA unless an app includes the AdSupport.framework for ad functionality. We are seeking clarification with Apple and we will update our affected customers as we learn more over the next several days."
Flurry just released the version 4.3.2 of their SDK, which specifically address that problem.
Turns out the Testflight v2.2.0 was the conflict. They have since fixed it according to their changelog: Consolidate both SDK versions into one which removes all access to ASIdentifierManager
Crashlytics was the problem. We had a few apps rejected because of it. But I already talked with Crashlytics and they released a new update today (version 2.1.6) which fix this issue.
Several libraries have the AdSupport.framework but they do not use it unless specifically called. Crashlytics was calling the framework because it had to check if the app had support for ads. And that change was implemented on version 2.1.5
So if you are using crashlytics, that's the most probable reason. To fix that, just re-archive your app so crashlytics can use the new version with this fix.
Response from Crashlytics Team:
"We just pushed out an update for this- can you build and run your app again with the Mac app open so it can update your SDK? You'll be all good to go after that! Keep me posted after you resubmit :)"
PS: This is starting to happen because Apple seem to have changed their policy for ADSupport usage.
I'd previously written the following in comments, directing people to the "strings" or "otool" terminal commands. However, I really like the suggested answer of using grep. So you can try it first. My suggestion is to prepend "git" to that command, because it's so much faster:
git grep advertisingIdentifier
If that doesn't work, then try (as posted earlier):
grep -r advertisingIdentifier .
What follows is what I'd previously written in a comment above, as a how-to for terminal commands:
You can search your project's files in Xcode or you can try removing the AdSupport framework to see what fails at build/run time.
To use the terminal, click Spotlight (search) and type Terminal. Wait for it to appear as an Application in the search results.
Once in Terminal, type "cd" followed by a space, then drag and drop your Xcode build folder from Finder into Terminal. This should automatically type that folder name in. Hit Enter, and it will change directories (cd) you to that folder.
From there, type strings then a space, then the filename for your library or otool, a space and the filename for library. You should be able to hit TAB to auto-complete filenames.
My app was also rejected with the same error! I found an occurrence of advertisingIdentifier in the latest Facebook SDK (3.12). Maybe you can check your library's for an occurence with the method below:
I opened the FacebookSDK.framework as a library in the terminal and typed the following command
otool -v -s __TEXT __objc_methname FacebookSDK | grep advertisingIdentifier
But I don't know what to do. Was my app rejected because of this reference? If yes what to do if I want to use facebook functionalities in my app?
This is a bit more complicated than it seems on the surface. After some experimentation I found that the AdSupport Framework is linked even if only directly accessing classes that are referenced in the AdSupport Framework. Ironically, [AsIdentifierManager class], which is used in a lot of third-party libraries to check whether or not the AdSupport Framework has been linked, will actually cause the AdSupport Framework to be linked. Obfuscating the class by using NSClassFromString(#"AsIdentfierManager") will not cause the AdSupport framework to be automatically linked. Of course, most of the time this code will be in third-party libraries so you won't have much control over it, however, this is what's going on.
I built an example project on GitHub that illustrates this behavior using Segment.io's framework.
https://github.com/distefam/AdSupportDemo
Flurry Analytics uses this API as well.
Terminal output:
Binary file ./Lib/Flurry/libFlurry_4.3.0.a matches
Flurry says that the selector is not called if AdSupport framework isn't linked.
So I removed the framework and tried submitting again.
I had a working application, and then I learned to use cocoapods and I installed CWPopup. I had not tried to run the app since I started using the .xcworkspace instead of .xcodeproj so I think that may be the problem, but I'm not sure.
I had zero errors and then I tried to run it and now I have 14 errors, all saying Apple Mach-O Linker Error. Underneath each one I see different things mentioning twitter and facebook seesions and requests and such. I don't even use twitter or facebook in my app, this is a very basic app.
This error says that you lost some required frameworks or libraries in your project. Check in your Targets->Build Phases-> Link Binary With Labraries is all required frameworks and libraries added.
This was simply an update that didn't change anything to do with the rejection reason. Here is the response from the resolution center:
Reasons
Program License Agreement
PLA 3.3.12
We found your app uses the iOS Advertising Identifier but does not include ad functionality. This does not comply with the terms of the iOS Developer Program License Agreement, as required by the App Store Review Guidelines.
Specifically, section 3.3.12 of the iOS Developer Program License Agreement states:
"You and Your Applications (and any third party with whom you have contracted to serve advertising) may use the Advertising Identifier, and any information obtained through the use of the Advertising Identifier, only for the purpose of serving advertising. If a user resets the Advertising Identifier, then You agree not to combine, correlate, link or otherwise associate, either directly or indirectly, the prior Advertising Identifier and any derived information with the reset Advertising Identifier."
Please check your code - including any third-party libraries - to remove any instances of:
class: ASIdentifierManager
selector: advertisingIdentifier
framework: AdSupport.framework
If you are planning to incorporate ads in a future version, please remove the Advertising Identifier from your app until you have included ad functionality.
To help locate the Advertising Identifier, use the “nm” tool. For information on the “nm” tool, open a terminal window and enter, “man nm.”
If you do not have access to the libraries source, you may be able to search the compiled binary using the "strings" or "otool" command line tools. The "strings" tool lists the methods that the library calls, and "otool -ov" will list the Objective-C class structures and their defined methods. These techniques can help you narrow down where the problematic code resides.
The third party libraries I'm using is the latest version of parse.com sdk, latest version of flurry analytics, and version 2.2 of test flight. Does anybody know which library is the issue? Thanks
In Terminal:
Go to the root folder of your project
Type: grep -r advertisingIdentifier . (the dot at the end is critical)
This will recursively check every file, and give you the name of the offending library.
(in my case, it was Flurry)
Update
Google released Google Analytics Services iOS SDK v3.03c which removes the AdSupport.framework dependency by default.
Full changelog entry for Release Version 3.03c (February 19, 2014): https://developers.google.com/analytics/devguides/collection/ios/changelog
Old Awnser
My problem was with Google Analytics and TestFlight.
For TestFlight I just update the library to the version 2.2.1 (https://www.testflightapp.com/sdk/ios/release_notes/2.2.1/).
But for updating Google Analytics I had to remove the -ObjC flag. But as I use Cocoapods to manage some of third libraries, I couldn't just remove it. So I did the follow:
1 - started updating the libGoogleAnalytics.a to Version 3.03a (February 5, 2014)
2 - then a removed also the AdSupport.framework
3 - added "-force_load\ "${PROJECT_DIR}/Source/Library/GoogleAnalyticsServicesiOS_3.03a"" under "Target --> Build Settings --> Other Linker Flags"
(Note that in my project the GoogleAnalytics is inside /Source/Library/ folder, and you have to configure your own)
But as I coudn't remove -ObjC flag I searched for how to use -force_load flag with Cocoapods, then I found two useful links:
1 - https://github.com/CocoaPods/CocoaPods/issues/712
2 - http://www.deanmao.com/2012/12/31/linker-error-using-cocoapods/
To summarize I changed the -ObjC flag for "-force_load $(TARGET_BUILD_DIR)/libPods.a" also under "Target --> Build Settings --> Other Linker Flags"
But again, when I tried to publish my app I got an error telling me that the compiler didn't find libPods.a, so I went to "Target --> Build Settings --> Other Linker Flags --> Release" and change this string $(TARGET_BUILD_DIR) to ${BUILT_PRODUCTS_DIR}.
So my Other Linker Flags became like the image below.
Hope to help somebody.
Sorry for my english.
=]
For me, Flurry Analytics and TestFlight were both the problem.
For TestFlight, it's as easy as updating it. The 2.2.1 version won't cause any problem (I checked using strings, as Apple suggest)
For Flurry, there is currently no fix apart from removing Flurry, and contrary to Lou Weed suggestion, even if AdSupport.framework is not linked, your app will be rejected.
Here is Flurry support answer :
"Thank you for reaching out to Flurry. We have recently learned that Apple has rejected some apps it believes are using the Identifier for Advertising (IDFA) without including ad functionality. Please note that Flurry does not collect the IDFA unless an app includes the AdSupport.framework for ad functionality. We are seeking clarification with Apple and we will update our affected customers as we learn more over the next several days."
Flurry just released the version 4.3.2 of their SDK, which specifically address that problem.
Turns out the Testflight v2.2.0 was the conflict. They have since fixed it according to their changelog: Consolidate both SDK versions into one which removes all access to ASIdentifierManager
Crashlytics was the problem. We had a few apps rejected because of it. But I already talked with Crashlytics and they released a new update today (version 2.1.6) which fix this issue.
Several libraries have the AdSupport.framework but they do not use it unless specifically called. Crashlytics was calling the framework because it had to check if the app had support for ads. And that change was implemented on version 2.1.5
So if you are using crashlytics, that's the most probable reason. To fix that, just re-archive your app so crashlytics can use the new version with this fix.
Response from Crashlytics Team:
"We just pushed out an update for this- can you build and run your app again with the Mac app open so it can update your SDK? You'll be all good to go after that! Keep me posted after you resubmit :)"
PS: This is starting to happen because Apple seem to have changed their policy for ADSupport usage.
I'd previously written the following in comments, directing people to the "strings" or "otool" terminal commands. However, I really like the suggested answer of using grep. So you can try it first. My suggestion is to prepend "git" to that command, because it's so much faster:
git grep advertisingIdentifier
If that doesn't work, then try (as posted earlier):
grep -r advertisingIdentifier .
What follows is what I'd previously written in a comment above, as a how-to for terminal commands:
You can search your project's files in Xcode or you can try removing the AdSupport framework to see what fails at build/run time.
To use the terminal, click Spotlight (search) and type Terminal. Wait for it to appear as an Application in the search results.
Once in Terminal, type "cd" followed by a space, then drag and drop your Xcode build folder from Finder into Terminal. This should automatically type that folder name in. Hit Enter, and it will change directories (cd) you to that folder.
From there, type strings then a space, then the filename for your library or otool, a space and the filename for library. You should be able to hit TAB to auto-complete filenames.
My app was also rejected with the same error! I found an occurrence of advertisingIdentifier in the latest Facebook SDK (3.12). Maybe you can check your library's for an occurence with the method below:
I opened the FacebookSDK.framework as a library in the terminal and typed the following command
otool -v -s __TEXT __objc_methname FacebookSDK | grep advertisingIdentifier
But I don't know what to do. Was my app rejected because of this reference? If yes what to do if I want to use facebook functionalities in my app?
This is a bit more complicated than it seems on the surface. After some experimentation I found that the AdSupport Framework is linked even if only directly accessing classes that are referenced in the AdSupport Framework. Ironically, [AsIdentifierManager class], which is used in a lot of third-party libraries to check whether or not the AdSupport Framework has been linked, will actually cause the AdSupport Framework to be linked. Obfuscating the class by using NSClassFromString(#"AsIdentfierManager") will not cause the AdSupport framework to be automatically linked. Of course, most of the time this code will be in third-party libraries so you won't have much control over it, however, this is what's going on.
I built an example project on GitHub that illustrates this behavior using Segment.io's framework.
https://github.com/distefam/AdSupportDemo
Flurry Analytics uses this API as well.
Terminal output:
Binary file ./Lib/Flurry/libFlurry_4.3.0.a matches
Flurry says that the selector is not called if AdSupport framework isn't linked.
So I removed the framework and tried submitting again.
This was simply an update that didn't change anything to do with the rejection reason. Here is the response from the resolution center:
Reasons
Program License Agreement
PLA 3.3.12
We found your app uses the iOS Advertising Identifier but does not include ad functionality. This does not comply with the terms of the iOS Developer Program License Agreement, as required by the App Store Review Guidelines.
Specifically, section 3.3.12 of the iOS Developer Program License Agreement states:
"You and Your Applications (and any third party with whom you have contracted to serve advertising) may use the Advertising Identifier, and any information obtained through the use of the Advertising Identifier, only for the purpose of serving advertising. If a user resets the Advertising Identifier, then You agree not to combine, correlate, link or otherwise associate, either directly or indirectly, the prior Advertising Identifier and any derived information with the reset Advertising Identifier."
Please check your code - including any third-party libraries - to remove any instances of:
class: ASIdentifierManager
selector: advertisingIdentifier
framework: AdSupport.framework
If you are planning to incorporate ads in a future version, please remove the Advertising Identifier from your app until you have included ad functionality.
To help locate the Advertising Identifier, use the “nm” tool. For information on the “nm” tool, open a terminal window and enter, “man nm.”
If you do not have access to the libraries source, you may be able to search the compiled binary using the "strings" or "otool" command line tools. The "strings" tool lists the methods that the library calls, and "otool -ov" will list the Objective-C class structures and their defined methods. These techniques can help you narrow down where the problematic code resides.
The third party libraries I'm using is the latest version of parse.com sdk, latest version of flurry analytics, and version 2.2 of test flight. Does anybody know which library is the issue? Thanks
In Terminal:
Go to the root folder of your project
Type: grep -r advertisingIdentifier . (the dot at the end is critical)
This will recursively check every file, and give you the name of the offending library.
(in my case, it was Flurry)
Update
Google released Google Analytics Services iOS SDK v3.03c which removes the AdSupport.framework dependency by default.
Full changelog entry for Release Version 3.03c (February 19, 2014): https://developers.google.com/analytics/devguides/collection/ios/changelog
Old Awnser
My problem was with Google Analytics and TestFlight.
For TestFlight I just update the library to the version 2.2.1 (https://www.testflightapp.com/sdk/ios/release_notes/2.2.1/).
But for updating Google Analytics I had to remove the -ObjC flag. But as I use Cocoapods to manage some of third libraries, I couldn't just remove it. So I did the follow:
1 - started updating the libGoogleAnalytics.a to Version 3.03a (February 5, 2014)
2 - then a removed also the AdSupport.framework
3 - added "-force_load\ "${PROJECT_DIR}/Source/Library/GoogleAnalyticsServicesiOS_3.03a"" under "Target --> Build Settings --> Other Linker Flags"
(Note that in my project the GoogleAnalytics is inside /Source/Library/ folder, and you have to configure your own)
But as I coudn't remove -ObjC flag I searched for how to use -force_load flag with Cocoapods, then I found two useful links:
1 - https://github.com/CocoaPods/CocoaPods/issues/712
2 - http://www.deanmao.com/2012/12/31/linker-error-using-cocoapods/
To summarize I changed the -ObjC flag for "-force_load $(TARGET_BUILD_DIR)/libPods.a" also under "Target --> Build Settings --> Other Linker Flags"
But again, when I tried to publish my app I got an error telling me that the compiler didn't find libPods.a, so I went to "Target --> Build Settings --> Other Linker Flags --> Release" and change this string $(TARGET_BUILD_DIR) to ${BUILT_PRODUCTS_DIR}.
So my Other Linker Flags became like the image below.
Hope to help somebody.
Sorry for my english.
=]
For me, Flurry Analytics and TestFlight were both the problem.
For TestFlight, it's as easy as updating it. The 2.2.1 version won't cause any problem (I checked using strings, as Apple suggest)
For Flurry, there is currently no fix apart from removing Flurry, and contrary to Lou Weed suggestion, even if AdSupport.framework is not linked, your app will be rejected.
Here is Flurry support answer :
"Thank you for reaching out to Flurry. We have recently learned that Apple has rejected some apps it believes are using the Identifier for Advertising (IDFA) without including ad functionality. Please note that Flurry does not collect the IDFA unless an app includes the AdSupport.framework for ad functionality. We are seeking clarification with Apple and we will update our affected customers as we learn more over the next several days."
Flurry just released the version 4.3.2 of their SDK, which specifically address that problem.
Turns out the Testflight v2.2.0 was the conflict. They have since fixed it according to their changelog: Consolidate both SDK versions into one which removes all access to ASIdentifierManager
Crashlytics was the problem. We had a few apps rejected because of it. But I already talked with Crashlytics and they released a new update today (version 2.1.6) which fix this issue.
Several libraries have the AdSupport.framework but they do not use it unless specifically called. Crashlytics was calling the framework because it had to check if the app had support for ads. And that change was implemented on version 2.1.5
So if you are using crashlytics, that's the most probable reason. To fix that, just re-archive your app so crashlytics can use the new version with this fix.
Response from Crashlytics Team:
"We just pushed out an update for this- can you build and run your app again with the Mac app open so it can update your SDK? You'll be all good to go after that! Keep me posted after you resubmit :)"
PS: This is starting to happen because Apple seem to have changed their policy for ADSupport usage.
I'd previously written the following in comments, directing people to the "strings" or "otool" terminal commands. However, I really like the suggested answer of using grep. So you can try it first. My suggestion is to prepend "git" to that command, because it's so much faster:
git grep advertisingIdentifier
If that doesn't work, then try (as posted earlier):
grep -r advertisingIdentifier .
What follows is what I'd previously written in a comment above, as a how-to for terminal commands:
You can search your project's files in Xcode or you can try removing the AdSupport framework to see what fails at build/run time.
To use the terminal, click Spotlight (search) and type Terminal. Wait for it to appear as an Application in the search results.
Once in Terminal, type "cd" followed by a space, then drag and drop your Xcode build folder from Finder into Terminal. This should automatically type that folder name in. Hit Enter, and it will change directories (cd) you to that folder.
From there, type strings then a space, then the filename for your library or otool, a space and the filename for library. You should be able to hit TAB to auto-complete filenames.
My app was also rejected with the same error! I found an occurrence of advertisingIdentifier in the latest Facebook SDK (3.12). Maybe you can check your library's for an occurence with the method below:
I opened the FacebookSDK.framework as a library in the terminal and typed the following command
otool -v -s __TEXT __objc_methname FacebookSDK | grep advertisingIdentifier
But I don't know what to do. Was my app rejected because of this reference? If yes what to do if I want to use facebook functionalities in my app?
This is a bit more complicated than it seems on the surface. After some experimentation I found that the AdSupport Framework is linked even if only directly accessing classes that are referenced in the AdSupport Framework. Ironically, [AsIdentifierManager class], which is used in a lot of third-party libraries to check whether or not the AdSupport Framework has been linked, will actually cause the AdSupport Framework to be linked. Obfuscating the class by using NSClassFromString(#"AsIdentfierManager") will not cause the AdSupport framework to be automatically linked. Of course, most of the time this code will be in third-party libraries so you won't have much control over it, however, this is what's going on.
I built an example project on GitHub that illustrates this behavior using Segment.io's framework.
https://github.com/distefam/AdSupportDemo
Flurry Analytics uses this API as well.
Terminal output:
Binary file ./Lib/Flurry/libFlurry_4.3.0.a matches
Flurry says that the selector is not called if AdSupport framework isn't linked.
So I removed the framework and tried submitting again.