I have a C++ solution in VS2008 with multiple projects. This solution contains files that are needed at runtime, which are loaded according to a path relative to the solution directory (e.g. "Testing/data/" + "dataN.bin"
).
In order for this solution to work, I must set the working directory setting in the project(s) so that it will point to the solution directory (e.g. Configuration Properties >> Debugging >> Working Directory = $(SolutionDir)
). This works fine when i'm debugging on my own PC. However, when a different user loads my solution, his projects does not have this property set properly.
I have traced this setting to be stored not in the project file (PROJECT.vcproj
), but in the user-specific file created for it (PROJECT.vcproj.DOMAIN.USER.user
).
I would like a way for this setting to be stored for ALL users, without having to set it manually again and again.
My thoughts were:
- Find a way to store this in the .vcproj file (not the user-specific one) or the solution file.
- Find a way to create a "default-user-specific file", from which all user-specific settings will start out (and can modify at will later).
However, I did not find a way to do either of these.
A few more notes / constraints:
- I need to work with many big files as these resources, therefore I would like to avoid performing copies to different directories.
- The solutions needs to support multiple build configurations (debug, release, etc.).
- I would like to avoid pre/post build scripts if possible, to keep things straightforward (low priority).
Any help will be appreciated... thanks in advance.
No such property exists. There are bigger issues, this also needs to work after you deploy your solution. The working directory then is not going to be a "solution" directory, there isn't one on the target machine.
You are much better off working from the assumption that the working directory is the same as the EXE directory. That will be the default both while debugging and on the target machine. You have full control over the location of the EXE file with a linker setting. And you can protect yourself from a shortcut running your program with another working directory by obtaining the EXE directory in your code so you can generate an absolute path. Use GetModuleFileName(), pass NULL to get the path to the EXE file.
Another standard solution is to copy any kind of resources the EXE needs to a folder that's relative from the build output folder. You do this with a Pre-Build event, make the command line look similar to this:
if not exist "$(OutDir)\Testing" md "$(OutDir)\Testing"
xcopy /d /s "$(SolutionDir)\Testing\*.*" "$(OutDir)\Testing
Note how the /d option ensures that copying is only done if the Testing folder content changed.
- Configure your Debugging settings as usual (set working directory, set parameters etc...) but use only relative paths, variables. DO NOT use absolute paths like D:\MyProject\libs
- Save your solution and then close Visual Studio.
- Go to your project directory and find PROJECT.vcproj.COMPUTERNAME.USER.user
- Rename it to PROJECT.vcproj.user (This file will be the generic debugging configuration, you may commit it to source control)
- Open up Visual Studio, make your extra additions to your debugging settings if required. (Extra information will be stored on PROJECT.vcproj.COMPUTERNAME.USER.user file which is specific to you. Note that PROJECT.vcproj.COMPUTERNAME.USER.user will override inherited configuration)
Sample PROJECT.vcproj.user file is provided below
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioUserFile
ProjectType="Visual C++"
Version="9,00"
ShowAllFiles="false"
>
<Configurations>
<Configuration
Name="Release|Win32"
>
<DebugSettings
Command="$(ProjectDir)..\Deploy\$(ConfigurationName)\$(TargetFileName)"
WorkingDirectory="$(ProjectDir)..\Deploy\$(ConfigurationName)\"
CommandArguments=""
Attach="false"
DebuggerType="3"
Remote="1"
RemoteMachine="LOCALHOST"
RemoteCommand=""
HttpUrl=""
PDBPath=""
SQLDebugging=""
Environment=""
EnvironmentMerge="true"
DebuggerFlavor="0"
MPIRunCommand=""
MPIRunArguments=""
MPIRunWorkingDirectory=""
ApplicationCommand=""
ApplicationArguments=""
ShimCommand=""
MPIAcceptMode=""
MPIAcceptFilter=""
/>
</Configuration>
<Configuration
Name="Debug|Win32"
>
<DebugSettings
Command="$(ProjectDir)..\Deploy\$(ConfigurationName)\$(TargetFileName)"
WorkingDirectory="$(ProjectDir)..\Deploy\$(ConfigurationName)\"
CommandArguments=""
Attach="false"
DebuggerType="3"
Remote="1"
RemoteMachine="LOCALHOST"
RemoteCommand=""
HttpUrl=""
PDBPath=""
SQLDebugging=""
Environment=""
EnvironmentMerge="true"
DebuggerFlavor="0"
MPIRunCommand=""
MPIRunArguments=""
MPIRunWorkingDirectory=""
ApplicationCommand=""
ApplicationArguments=""
ShimCommand=""
MPIAcceptMode=""
MPIAcceptFilter=""
/>
</Configuration>
</Configurations>
</VisualStudioUserFile>
You might consider using either 'Configuration Properties/ General/ Output Directory', or 'Configuration Properties/ Linker/ Output file', instead of the 'Debugger/ working directory' setting. These settings are per-project and not per-user, and if you leave the working directory intact this is the default value for the app working directory.
I wonder whether this would be possible since a user might not have enough rights to access and read/write to the directory, I suppose VS checks if a user has access to a directory when you choose it that is probably why there is only an account based option.