How do I include my own xcconfigs when using Cocoapods? - cocoapods

Is there a way to specify in the Podfile that an xcconfig file should be #included in the the one generated by Cocoapods?
Is there an exposed method/variable for appending this #include or do I need to read the generated xcconfig and regurgitate it with the additional text?
For instance, in the generated Pods-SomeTarget.[configuration].xcconfig, I'd like to see:
#include "my_other_config.xcconfig" //<-- I want this to be inserted
FRAMEWORK_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Crashlytics" "${PODS_ROOT}/Fabric" "${PODS_ROOT}/Google-Mobile-Ads-SDK/Frameworks" "${PODS_ROOT}/GoogleAds-IMA-iOS-SDK-For-AdMob/GoogleInteractiveMediaAds/GoogleInteractiveMediaAds-GoogleIMA3ForAdMob" "${PODS_ROOT}/NewRelicAgent/NewRelicAgent" "${PODS_ROOT}/TwitterCore/iOS" "${PODS_ROOT}/TwitterKit/iOS"
GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1

Include these lines in your debug and release xcconfig files, respectively:
#include "Pods/Target Support Files/Pods-Used/Pods-Used.debug.xcconfig"
#include "Pods/Target Support Files/Pods-Used/Pods-Used.release.xcconfig"
Then click on your project and in the detail navigation bar on the left switch from your current target to your project and select Info at the top. Set the project to use your base/shared config file and Debug/Release to point to your xcconfig files.

Related

CMake: GCC preprocessor IMACROS file change does not trigger rebuild

I'm using the -imacros option for GCC in order to set all preprocessor defines (Options) for a project.
Before imacros I have been using a raw file with the preprocessor defines names and with a regular expression in CMAKE I was creating the list of -D to put in the CMAKE_C_FLAGS.
This works fine but ugly to see in the text editor. So to enhance that, I have changed to -imacros.
CMAKE_C_FLAGS will contain -imacros "path to configuration header"
This works fine, but if I change some configuration item in the configuration header the CMAKE do not recompile the file (don't see changes). In the old version - as you can expect - if some -D was changed all the files will be recompiled.
Any help?
An simple Approach
You can use OBJECT_DEPENDS source file property. But that needs to be set for all source files with something like:
set_source_files_properties(
${sources}
PROPERTIES
OBJECT_DEPENDS "path to configuration header"
)
Alternatives for all Source Files in Project
Officially CMake recommends to put all your definitions in a header file that is included by all your source files. The header could e.g. be generated from a template using configure_file().
But to follow your line of thought with using -imacros compiler flag, here are two alternative approaches for triggering a rebuild of all source files if "path to configuration header" file changes:
You can extend the scope of OBJECT_DEPENDS to all targets and their source files in the current directory with define_property(... INHERITED ...):
If the INHERITED option then the get_property() command will chain up to the next higher scope when the requested property is not set in the scope given to the command. DIRECTORY scope chains to GLOBAL. TARGET, SOURCE, and TEST chain to DIRECTORY.
So in your case this translates to:
define_property(
SOURCE
PROPERTY OBJECT_DEPENDS
INHERITED
BRIEF_DOCS "brief-doc"
FULL_DOCS "full-doc"
)
set_directory_properties(
PROPERTIES
OBJECT_DEPENDS "path to configuration header"
)
If I understand correctly, you anyway have to re-run CMake if your "configuration header" should/would change. Then you can simply add one definition outside your "configuration header" that keeps track of the header with something like:
file(TIMESTAMP "path to configuration header" _timestamp)
add_definitions(-DIMACROS_TIMESTAMP=${_timestamp})
Now every time your header gets a new timestamp, the definitions for all targets are changing and your build system will rebuild all source files.

Xcode Archive Build Fails

I have an Xcode 7.2 project that succeeds when building/running against the local device Product|Build. The main project include a reference to InAppSettingsKit project. When I try Product|Archive the build fails. Any help or suggestions will appreciated.
The main project has a bridging header file to InAppSettingsKit project. The problem seems to be that the header file referenced in the bridging header file is not found.
Bridging Header File
#ifndef Screen_Saver_Killer_InAppSettingsKit_Bridging_Header_h
#define Screen_Saver_Killer_InAppSettingsKit_Bridging_Header_h
#endif
#include <UIKit/UIKit.h>
#import "InAppSettingsKit/IASKViewController.h"
#import "InAppSettingsKit/IASKAppSettingsViewController.h"
#import "InAppSettingsKit/IASKSpecifierValuesViewController.h"
#import "InAppSettingsKit/IASKSpecifier.h"
#import "InAppSettingsKit/IASKSettingsReader.h"
#import <iAd/iAd.h>
As requested, here is the search paths of the main project:
(I noticed InAppSettingsKit.xcodeproj is in red; does that mean anything ?)
My problem was with InAppSettingsKit. Their website says: for Archive builds there's a minor annoyance: To make those work, you'll need to add $(OBJROOT)/UninstalledProducts/include to the HEADER_SEARCH_PATHS
This wasn't quite right either.
I think this is a bug in XCode 7.2 + Swift with Obj-C dependencies when archives are built.
I now know way more about xcode than I ever wanted to.
First you need to go through the install logs to find out where things are being built. On my installation $OBJROOT points to:
/Users/jlongo/Library/Developer/Xcode/DerivedData/PROJECTX-bmyyngijghtekdgqqfnabonhpuxo/Build/Intermediates/ArchiveIntermediates/PROJECTX/IntermediateBuildFilesPath
There I found the header files in the path:
.../IntermediateBuildFilesPath/iphoneos/include/InAppSettingsKit/
So my resolution ended up being (non-recursive)
$(OBJROOT)/UninstalledProducts/iphoneos/include
Interestingly, $(OBJROOT) or other recursive paths shorter than this one did not work.
Also I placed this setting in:
Main Project|**Targets**|Build Settings|Header Search Paths
setting it here will not work:
Main Project|**Project**|Build Settings|Header Search Paths

How do I use Boost Graph Library from Objective-C++?

Trying to figure out how to use BGL from within Objective-C++. Something is amiss. Steps to repro:
New Cocoa Application project.
Rename MyAppDelegate.m to MyAppDelegate.mm
Add #include <boost/shared_ptr.hpp> to MyAppDelegate.mm (works fine, assuming you have your header search paths set right.)
Add #include <boost/graph/adjacency_list.hpp> to MyAppDelegate.mm
Something transitively included by boost/graph/adjacency_list.hpp is colliding with some old Carbon headers that are being transitively imported by the Cocoa headers. Here is the output I see (the first error's worth anyway):
In file included from /Users/me/Documents/Projects/BoostTest/BoostTest/MyAppDelegate.mm:10:
In file included from /Users/me/Documents/Projects/BoostTest/boost/graph/adjacency_list.hpp:33:
In file included from /Users/me/Documents/Projects/BoostTest/boost/graph/graph_traits.hpp:27:
In file included from /Users/me/Documents/Projects/BoostTest/boost/pending/property.hpp:13:
In file included from /Users/me/Documents/Projects/BoostTest/boost/type_traits.hpp:35:
In file included from /Users/me/Documents/Projects/BoostTest/boost/type_traits/has_operator.hpp:12:
In file included from /Users/me/Documents/Projects/BoostTest/boost/type_traits/has_bit_and.hpp:43:
/Users/me/Documents/Projects/BoostTest/boost/type_traits/detail/has_binary_operator.hpp:154:42: error: expected member name or ';' after declaration specifiers
static ::boost::type_traits::yes_type check(has_operator); // this version is preferred when operator exists
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^
In file included from /Users/me/Documents/Projects/BoostTest/BoostTest/MyAppDelegate.mm:9:
In file included from /Users/me/Documents/Projects/BoostTest/BoostTest/MyAppDelegate.h:9:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/Foundation.framework/Headers/Foundation.h:76:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/Foundation.framework/Headers/NSURLError.h:12:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/CoreServices.framework/Headers/CoreServices.h:23:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/CoreServices.framework/Frameworks/AE.framework/Headers/AE.h:20:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/CarbonCore.h:115:
In file included from /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/Debugging.h:212:
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/usr/include/AssertMacros.h:1291:28: note: expanded from macro 'check'
#define check(assertion) __Check(assertion)
^
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/usr/include/AssertMacros.h:280:5: note: expanded from macro '__Check'
do \
^
If I remove the #import <Cocoa/Cocoa.h> from the project's prefix header, and then #include <boost/graph/adjacency_list.hpp> before including <Cocoa/Cocoa.h> in MyAppDelegate.mm things will compile, but this is sub-optimal/undesirable.
Is there something simple I can do (ideally in the prefix header so I don't have to do this everywhere) to make the Cocoa headers and the BGL headers co-exist peacefully?
Should have googled for epsilon more time before asking. Just after posting this I found this page which explains that adding the following line prior to including the Cocoa headers will do the trick:
#define __ASSERT_MACROS_DEFINE_VERSIONS_WITHOUT_UNDERSCORES 0
I had tried doing that in my individual MyAppDelegate.mm file, and it didn't work, but that was because of the prefix header. Adding it to the project's prefix header prior to its inclusion of Cocoa/Cocoa.h did the trick.

How to Generate Windows DLL versioning information with CMake

I'm using CMake to build a shared library, however for the Windows DLL I need the versioning information, like:
FileDescription
FileVersion
InternalName
LegalCopyright
OriginalFilename
ProductName
ProductVersion
So far, all I have are the VERSION and SOVERSION properties, but these don't seem to correlate to the FileVersion information I was expecting.
set(LIC_TARGET MySharedLib)
add_library(${LIC_TARGET} SHARED ${SOURCES} )
SET_TARGET_PROPERTIES(${LIC_TARGET}
PROPERTIES
VERSION ${MY_PRODUCT_NUMBER}.${MY_PRODUCT_VERSION}.${MY_BUILD_NUMBER}
SOVERSION ${MY_PRODUCT_NUMBER})
I've found manual methods (see example at the bottom) but would prefer to contain this within CMake.
Help?
You could use your CMake variable values in conjunction with a version.rc.in file and the configure_file command.
// version.rc.in
#define VER_FILEVERSION #MY_PRODUCT_NUMBER#,#MY_PRODUCT_VERSION#,#MY_BUILD_NUMBER#,0
#define VER_FILEVERSION_STR "#MY_PRODUCT_NUMBER#.#MY_PRODUCT_VERSION#.#MY_BUILD_NUMBER#.0\0"
#define VER_PRODUCTVERSION #MY_PRODUCT_NUMBER#,#MY_PRODUCT_VERSION#,#MY_BUILD_NUMBER#,0
#define VER_PRODUCTVERSION_STR "#MY_PRODUCT_NUMBER#.#MY_PRODUCT_VERSION#.#MY_BUILD_NUMBER#\0"
//
// ...along with the rest of the file from your "manual methods" reference
And then, in your CMakeLists.txt file:
# CMakeLists.txt
set(MY_PRODUCT_NUMBER 3)
set(MY_PRODUCT_VERSION 5)
set(MY_BUILD_NUMBER 49)
configure_file(
${CMAKE_CURRENT_SOURCE_DIR}/version.rc.in
${CMAKE_CURRENT_BINARY_DIR}/version.rc
#ONLY)
set(LIC_TARGET MySharedLib)
add_library(${LIC_TARGET} SHARED ${SOURCES}
${CMAKE_CURRENT_BINARY_DIR}/version.rc)
# Alternatively you could simply include version.rc in another rc file
# if there already is one in one of the files in ${SOURCES}
I'm had same problem and have automated version generation for my projects.
You need three files from github:
generate_product_version.cmake
VersionInfo.in
VersionResource.rc
Put it in cmake subdirectory of your project and make sure to include it to CMAKE_MODULE_PATH like:
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_SOURCE_DIR}/cmake)
Then before add_executable() or add_library(SHARED) your target, use:
include(generate_product_version)
generate_product_version(
VersionFilesOutputVariable
NAME "My Great Project"
ICON ${PATH_TO_APPLICATION_ICON}
VERSION_MAJOR 1
VERSION_MINOR 3
VERSION_PATCH ${BUILD_COUNTER}
VERSION_REVISION ${BUILD_REVISION}
)
Full list of supported resource strings see in generate_product_version.cmake.
VersionInfo.h and VersionResource.rc will be generated to cmake binaries folder. Variable VersionFilesOutputVariable will hold paths to these files. Just add this list to your target:
add_executable(MyGreatProject ${your-target-sources} ${VersionFilesOutputVariable})
UPDATE: Corrected generate_product_version script parameters from VERSION_PATH
to VERSION_PATCH.
There is an even easier way than the accepted answer. It does not involve transforming an input resource.rc.in. Simply create a generic version.rc file as described here and then from your CMakeLists.txt do this:
#CMakeLists.txt
add_definitions(-DVER_COMPANYNAME_STR="MyCompany")
add_definitions(-DVER_FILEVERSION_STR="1,1,0.0")
# ...
# add all the other defines here
set(LIC_TARGET MySharedLib)
add_library(${LIC_TARGET} SHARED ${SOURCES} version.rc)
This has the added benefit that the defines are accessible from your source code as well, so you have programmatic access to your version.

XCode include paths

I'm having a problem getting XCode to deal with a particular file structure that I am using or that I wish to use.
I have a set of files in the following form...
Library
Headers
Library
Package1
Header1.h
Header2.h
HeaderN.h
Package2
Header1.h
Header2.h
HeaderN.h
PackageN
Header1.h
Header2.h
HeaderN.h
Source
Package1
Source1.m
Source2.m
SourceN.m
Package2
Source1.m
Source2.m
SourceN.m
Package3
Source1.m
Source2.m
SourceN.m
The include model I want for code outside of this library is...
#import "Library/Package/Header.h"
I want to point XCode at Library/Headers but not at the internal folders. When I add this tree to the project XCode seems to make implicit include paths to every node in the tree.
Client code within the project but outside this tree can do this...
#import "Header.h"
instead of...
#import "Library/Package/Header.h"
I can't seem to find a way to dissallow the non-qualified form.
Any help would be appreciated.
Thanks,
-Roman
You're running up against Xcode's behaviour that it builds a flat-headermap. You can disable this by adding the build setting:
HEADERMAP_INCLUDES_FLAT_ENTRIES_FOR_TARGET_BEING_BUILT=NO
to your project settings.
If you include the headers in files in the project then XCode will always find them without path qualification, as you've discovered. The best solution is to remove the headers from the project and specify "Library/Headers" as a header search path in your project settings. The headers won't show in your project, but they also won't be implicitly found by XCode while compiling, either; client code will have to specify the full path off of "Library/Headers" to get to the header file they want.

Resources