To make sure we can share Xcode projects via git and have them work without requiring modification, we will define Grid environment variables. To make sure these environment variables will be available to the Xcode build system, issue the following shell command:
* Click on *New Document*. Paste the following into the new script, editing the paths appropriately (just replace `user_id` with your *user_id* if you are unsure):
```apple script
do shell script "launchctl setenv Grid $HOME/src/Grid
launchctl setenv GridPre $HOME/bin
launchctl setenv GridPkg /opt/local"
```
* Save the script inside `~/Applications` and give it the name `GridEnv.app`.
* Open `System Preferences`, `Users & Groups`
* Click on `Login Items`
* Click the plus sign to add a new login item
* Select the `~/Applications` folder and select `GridEnv.app`
Log out and in again.
### Method 2 -- `environment.plist`
Make the file `environment.plist` in `~/Library/LaunchAgents` with the following contents, editing the paths appropriately (just replace `user_id` with your *user_id* if you are unsure):
```html
<?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">
<plistversion="1.0">
<dict>
<key>Label</key>
<string>Grid.startup</string>
<key>ProgramArguments</key>
<array>
<string>sh</string>
<string>-c</string>
<string>launchctl setenv Grid $HOME/src/Grid
launchctl setenv GridPre $HOME/bin
launchctl setenv GridPkg /opt/local</string>
</array>
<key>RunAtLoad</key>
<true/>
</dict>
</plist>
```
## 3. Install and build Open MPI -- ***optional***
Download the latest version of [Open MPI][OMPI] version 3.1 (I used 3.1.3).
NB: Grid does not have any dependencies on fortran, however many standard scientific packages do, so you may as well download GNU fortran (e.g. MacPorts ``gfortran`` package) and build Open MPI like so:
Install [Homebrew][Homebrew] if you haven't done so already, and then install packages with:
sudo brew install <packagename>
The same packages are available as from MacPorts.
### Install LIME ***optional***
There isn't currently a port for [C-LIME][C-LIME], so download the source and then build it:
[C-LIME]: https://usqcd-software.github.io/c-lime/ "C-language API for Lattice QCD Interchange Message Encapsulation / Large Internet Message Encapsulation"
Start by cloning [Grid (from GitHub)][Grid] ***into the directory you specified in*** `$Grid`. Bear in mind that git will create the `Grid` subdirectory to place Grid in, so for example if `$Grid` is set to `~/src/Grid` then install Grid with:
The Xcode build system supports multiple configurations for each project, by default: `Debug` and `Release`, but more configurations can be defined. We will create separate Grid build directories for each configuration, using the Grid **Autoconf** build system to make each configuration. NB: it is **not** necessary to run `make install` on them once they are built (IDE features such as *jump to definition* will work better of you don't).
Below are shown the `configure` script invocations for three recommended configurations. You are free to define more, fewer or different configurations, but as a minimum, be sure to build a `Debug` configuration.
This is the build for every day developing and debugging with Xcode. It uses the Xcode clang c++ compiler, without MPI, and defaults to double-precision. Xcode builds the `Debug` configuration with debug symbols for full debugging:
Since Grid itself doesn't really have debug configurations, the release build is recommended to be the same as `Debug`, except using single-precision (handy for validation):
Detailed instructions follow, but instead of following the instructions in this section, you can clone `HelloGrid` from the [University of Edinburgh GitLab site][HelloGrid].
* Click ‘macOS’, then in the ‘Application’ section choose ‘Command Line Tool’, then click ‘Next’
* Choose options for your new project:
* Product Name: HelloGrid
* Team: None
* Organisation Name: sopa
* Organisation Identifier: uk.ac.ed.ph
* Language: C++
* ... then click ‘Next’
* Choose a location for your project, e.g. `$HOME/src`. NB: The project and all it’s files will be created inside `$HOME/src/HelloGrid`. If you are using Git, you can put the new project under Git source control immediately, if you like. Now click ‘Create’.
## Configure your new application to use Grid
Click the project name (`HelloGrid`) in the project navigator pane on the left (command-1 if it's not visible), then click the project name (`HelloGrid`) under `PROJECT` in the second pane. Click the `Build Settings` tab on the right, then under that click `All` and `Combined`. You should see:
![Project settings](GridXcFig1.png)
We now need to make changes to two sections (these are listed in alphabetical order), bearing in mind that if you are not using MPI (or you gave your build directories different names) replace `build_mpidebug` and `build_mpirelease` with the directory names you used.
Obtain a list of header locations required by Grid by running the following from your Grid build directory (choose an MPI configuration if you built one, e.g. `MPIDebug`):
The header locations follow the `-I` switches. You can ignore the other switches, and you can ignore duplicate entries, which just mean that your package manager has installed multiple packages in the same location.
*Note: `grid-config` will output absolute paths. Make sure to replace absolute paths with environment variables (such as `$GridPre`) in your settings, so that the project will work unmodified for other collaborators downloading the same project from git.*
**Note: the easiest way to set this value is to put it all on one line, space separated, and edit the text to the right of `HEADER_SEARCH_PATHS`**, i.e.:
Obtain a list of library locations required by Grid by running the following from your Grid build directory (again, choose an MPI configuration if you built one, e.g. `MPIDebug`):
The easiest way to link to all required libraries is to obtain a list of all libraries required by Grid by running the following from your Grid build directory:
./grid-config --libs
and pasting the output ***with `-lGrid -lHadrons ` prepended*** (including the `-l` switches) directly into `OTHER_LDFLAGS`, e.g.:
First, specify command-line arguments. From the menu, select `Product`, then `Scheme`, then `Edit Scheme`. Select `Run` on the left, then select the `Arguments` tab on the right. Add the following to `Arguments passed on Launch`:
--grid 4.4.4.8
If your program will be manipulating files, it's a good idea to specify the working directory on the `Options` tab under `Use Custom Working Directory` (by default, Xcode launches the program inside the Xcode build folder).
Then click `Close`.
Let's set a breakpoint by clicking on:
Grid_finalize();
then from the menu selecting `Debug`, then `Breakpoints`, then `Add Breakpoint at Current Line`.
Now click on the `Play` button (the right pointing triangle just to the right of the maximise button) to run your program under the debugger. (You may see dialog boxes the first couple of times asking whether to allow MPI to receive network requests - say yes to these.)
The debug output pane opens at the bottom of Xcode, with output on the right (ending with `Hello Grid`) and local variables on the left i.e.:
![Running under the debugger](GridXcFig2.png)
See the Xcode documentation to learn about the debugger. When you're done, press `ctl-cmd-Y` to let the program run to completion.
You could tell Xcode to use mpirun to launch multiple copies of a target executable, however if you do this the debugger will attach to mpirun - not your target process.
2. From the `Debug` menu, select `Attach to Process by PID or Name ...`. In the `PID or Process Name` field, enter the name of your target. Then click `Attach`.
3. From a terminal session, locate and run your executable using `mpirun` (*the mangled name of the project build products will not be exactly the same as this example*):
4. From the `Debug` menu in Xcode, select `Attach to Process`, and other running instances of your application will appear at the top of the list. Attach to as many instances as you wish to debug.
`Search Paths` | `LIBRARY_SEARCH_PATHS` | remove `$Grid/build$(CONFIGURATION)/Grid $Grid/build$(CONFIGURATION)/Hadrons` from the start of the path
This sets the deployment location to the makefile build folders (but by default, targets will have `SKIP_INSTALL` set to `Yes`). The change to the paths is to make sure any executable targets link to the versions of the `Grid` and `Hadrons` libraries just built.
5. Set the following values for each of the `Grid` and `Hadrons` targets in `Build Settings`
Note that with this setup, the Xcode build system is not aware of dependencies of your targets on the grid libraries. So you can modify Grid and/or Hadrons headers if you need to, and build your target without rebuilding the entire Grid and Hadrons Libraries (you can manually force the Libraries to rebuild by making the `Libraries` scheme). You can instead configure target dependencies to `Grid` and `Hadrons` libraries in the Xcode build system, just remember to also remove `-lGrid -lHadrons` from the list under `OTHER_LDFLAGS` for the entire project.