Project file format
A project is a collection of Dassie source files that is compiled into a single assembly. The Dassie project system is based on the central project file dsconfig.xml that lies in the root directory of every project and is used to configure compiler settings and define resources. The content of such a file looks like this:
<?xml version="1.0" encoding="utf-8"?>
<DassieConfig FormatVersion="1.0">
<!--Settings, references and build profiles, see below-->
</DassieConfig>
The following documentation is about format version 1.0, which is the most recent version. Once the format is updated, the documentation for old versions will be archived in this repository.
General settings
These settings are at the top level of the XML tree and configure the behavior of the compiler as well as resources associated with the project.
| Name | Possible values | Description | Notes |
|---|---|---|---|
AdvancedErrorMessages |
true or false |
If true, every error message will visually display the code section where it originated. |
|
ApplicationType |
Console, WinExe, Installer or Library |
Sets the application type and required subsystem of the program. | |
AssemblyFileName |
Any string | Sets the file name of the generated assembly. | |
AssemblyManifest |
Any string | The path to a manifest file that contains Windows-specific configuration. | |
BuildDirectory |
Any string | Sets the directory containing build output files. | |
BuildLogOptions |
A list of XML elements | A list of build log devices to write log messages to. | |
BuildProfiles |
See below | Contains custom build profiles. See below for more info. | |
CacheSourceFiles |
true or false |
If true, caches source files to enable some incremental build capabilities. |
Not yet finished. |
CodeAnalysisConfiguration |
A list of XML elements | Configuration for the default code analyzer. | |
CompilerMessageRedirectionFile |
Any string | Sets the file the compiler writes logs and error messages to. | |
Configuration |
Debug or Release |
Determines which build configuration should be used. | |
DebugProfiles |
See below | Contains custom debug profiles. See below for more info. | The Dassie compiler itself does not have any debugging capabilties. This setting is used by integrated development environments. |
EmitPdb |
true or false |
Determines wheter to emit symbol information. | |
EnableMessageTimestamps |
true or false |
If true, all compiler messages include a timestamp. |
|
EnableOverflowChecks |
true or false |
If set, arithmetic operations check for overflow and throw an appropriate exception at runtime. | |
EnableTips |
true or false |
If true, some errors and warnings will display additional information to help resolve the issue. |
|
EntryPoint |
Any string | Sets the application entry point. The value of this property corresponds to the unique name of the method or function that is set as the entry point. | |
ErrorColor |
Any string | The color to use for error messages, in the format #RRGGBB. | |
Extensions |
See below | A list of transient extensions. | |
GenerateILFiles |
true or false |
If true, the compiler outputs human-readable .NET Intermediate Language (.il) files. |
|
GenerateNativeAppHost |
true or false |
If true, generates native host executables along with .NET assemblies. |
|
IconFile |
Any string | A file path to an icon file to use for the generated assembly. | |
IgnoreAllMessages |
true or false |
Determines if all compiler messages (not warnings or errors) should be ignored. | |
IgnoreAllWarnings |
true or false |
Determines if all compiler warnings should be ignored. | |
IgnoredMessages |
See below | A list of compiler messages and warnings that are ignored and will never be emitted. See below for more details. | |
IlOptimizations |
true or false |
Determines wheter to optimize generated IL (intermediate language). | |
ImplicitImports |
true or false |
Determines wheter or not the Dassie core library (Dassie.Core) and some modules such as stdout are implicitly imported into every file. true by default. |
|
ImplicitTypeAliases |
true or false |
Determines wheter or not to enable default type aliases for primitive types (such as int32 for System.Int32). true by default. |
|
IncludeDependencies |
true or false |
If true, all dependencies of the program are statically linked into a single file. |
|
KeepIntermediateFiles |
true or false |
Determines wheter or not to delete intermediate source files, which are generated by the compiler as it rewrites high-level language constructs to a lower-level representation. | |
MacroDefinitions |
See below | Sets user-defined macros. See below for more details. | |
MeasureElapsedTime |
true or false |
If true, the compilation time (in milliseconds) will be displayed after a build. |
|
MessageColor |
Any string | The color to use for error messages, in the format #RRGGBB. | |
NoStdLib |
true or false |
If enabled, the Dassie standard library (Dassie.Core.dll) is not implicitly referenced. |
|
PersistentResourceFile |
true or false |
The Dassie compiler generates a .res file containing all native resources contained in the program. By default, this file is deleted after the build. When this setting is enabled, it is kept. |
|
PersistentResourceScript |
true or false |
If enabled, also keeps the .rc file that was used to generate the native resource file. |
|
Platform |
Auto, x86, x64, Arm32 or Arm64 |
Specifies the processor architecture of generated assemblies. | |
PrintExceptionInfo |
true or false |
If true, prints the whole stack trace of an exception when one occurs in the compiler. |
|
References |
See below | Used to configure dependencies. See below for more details. | |
Resources |
See below | Used to configure native and managed resources. See below for more details. | |
RootNamespace |
Any string | Sets the root namespace (determined by the export keyword) of the project. If empty, it is set to the project name. |
|
RunAnalyzers |
true or false |
If true, automatically runs code analyzers before every build. |
|
Runtime |
Jit or Aot |
Determines which runtime to use for the execution of the generated executables. If this property is set to Aot, the compiler generates native executables for the current system and platform that are compiled ahead of time, along with regular .NET assemblies. |
|
RuntimeIdentifier |
Any valid .NET RID | Sets the OS and platform to use for ahead-of-time compilation. | |
TreatWarningsAsErrors |
true or false |
If true, all compiler warnings are treated like errors. |
|
Verbosity |
0, 1 or 2 | Sets the level of detail for compiler messages. At level 0, the only compiler messages are errors, warnings and code suggestions. At level 1, the compiler displays more advanced information about the build process. At level 2, the compiler provides in-depth diagnostic information. | |
VersionInfo |
See below | Sets version information for the program. See below for more details. | |
WarningColor |
Any string | The color to use for warning messages, in the format #RRGGBB. |
Build profiles
Build profiles are used in combination with the dc build [BuildProfile] command and configure the scope of a build as well as custom settings and build events. Here is an example of a build profile:
<BuildProfiles>
<BuildProfile Name="BuildAndLog">
<Arguments>build</Arguments>
<PostBuildEvents>
<BuildEvent>
<Command>echo. >> build.log & echo Build finished at %time% on $(Date). >> build.log</Command>
</BuildEvent>
</PostBuildEvents>
</BuildProfile>
</BuildProfiles>
The above example first launches the compiler with the default arguments and then appends some text to a log file after the build is completed. The following tables list all features supported by build events:
<BuildProfile> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
Name |
Attribute | Any string | Sets the name of the build profile. |
Arguments |
Element | Any string | Sets the arguments with which the compiler is invoked when the build profile is executed. |
Settings |
Element | Children of the <DassieConfig> object |
Allows overriding the compiler settings from the table above. |
PreBuildEvents |
Element | A list of <BuildEvent>s |
A list of build events executed before the project is being built. |
PostBuildEvents |
Element | A list of <BuildEvent>s |
A list of build events executed after the project has been built. |
<BuildEvent> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
Critical |
Attribute | true or false |
If true, the compiler emits an error if the command returns a non-zero exit code. Otherwise, a warning is emitted. true by default. |
Hidden |
Attribute | true or false |
If true, the command is run in the background without a visible output. false by default. |
RunAsAdministrator |
Attribute | true or false |
If true, the command runs with full privileges. false by default. |
WaitForExit |
Attribute | true or false |
If true, the compiler waits for the command to finish execution before continuing. If disabled, no error or warning messages regarding the exit code are emitted. false by default. |
Command |
Element | Any string | The command that is executed when the build event is run. |
Debug profiles
Debug profiles are used by a debugging environment to configure arguments passed to the debuggee. Their markup structure looks like this:
<DebugProfiles>
<DebugProfile Name="Default">
<Arguments>file.txt</Arguments>
<WorkingDirectory>.\child</WorkingDirectory>
</DebugProfile>
</DebugProfiles>
<DebugProfile> has the following options:
| Name | Type | Allowed values | Description |
|---|---|---|---|
Name |
Attribute | Any string | Sets the name of the profile. |
Arguments |
Attribute | Any string | Sets the command-line arguments passed to the debuggee. |
WorkingDirectory |
Attribute | Any string | Sets the directory the debuggee is launched in. |
Ignoring compiler messages
The <IgnoredMessages> object is used to disable specific compiler error codes. Only information and warning messages can be ignored. To disable a message, add a child node corresponding to the kind of message that is to be disabled (information, warning) containing its error code. A list of error codes can be found here.
<IgnoredMessages>
<Message>DS0070</Message>
</IgnoredMessages>
References
References are used to declare dependencies on assemblies, other Dassie projects or NuGet packages. Here is an example:
<References>
<AssemblyReference>C:\libs\sdk.dll</AssemblyReference>
<ProjectReference>%userprofile%\Projects\Library\dsconfig.xml</ProjectReference>
<PackageReference Version="2.4.1">Package01</PackageReference>
</References>
The structure of these elements is described below.
<AssemblyReference> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
CopyToOutput |
Attribute | true or false |
Determines wheter or not to copy the referenced file to the build output directory. true by default. |
| Text | Any string | The path to the referenced file. |
<ProjectReference> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
CopyToOutput |
Attribute | true or false |
Determines wheter or not to copy the output of the referenced project to the build output directory. true by default. |
| Text | Any string | The project file of the referenced project. |
<PackageReference> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
Version |
Attribute | Any string | Determines which version of the package to reference. |
| Text | Any string | The NuGet package ID of the referenced package. |
Resources
There are two kinds of resources which can be included in a .NET assembly: Native (unmanaged) resources, which are stored in the .rsrc section of the PE file and are handled by the operating system, and managed resources that are handled by the .NET runtime. Here is an example:
<Resources>
<UnmanagedResource>version.res</UnmanagedResource>
<ManagedResource Name="Painting">image.png</ManagedResource>
</Resources>
These two types of resources have the following options:
<UnmanagedResource> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
| Text | Any string | The path to the resource file. |
<ManagedResource> object
| Name | Type | Allowed values | Description |
|---|---|---|---|
Name |
Attribute | Any string | An alias that identifies the resource inside the program. |
| Text | Any string | The path to the resource file. |
Version information
Version information is used to display metadata about the program. It is visible in the 'Details' tab of a file's properties in Windows.
<VersionInfo>
<Description>My program</Description>
<Copyright>(C) 2024 My company</Copyright>
</VersionInfo>
These fields are supported by the <VersionInfo> object:
| Name | Description |
|---|---|
Description |
A short description of the application. |
Product |
The product name of the application. |
InternalName |
The internal name of the application. |
Company |
The author of the application. |
Copyright |
A copyright string. |
Trademark |
Trademarks owned by the company. |
Version |
The product version of the application. |
FileVersion |
The file version of the application. |
Macros
Macros are identifiers that are replaced with a specific value by the compiler before the start of the compilation. In addition to a set of predefined macros, a project file can contain custom macro declarations. Macro names are always case-insensitive. Here is an example of how macros are used:
<VersionInfo>
<!--Assuming the year is 2024, this will be expanded to "(C) 2024 My company".-->
<Copyright>(C) $(Year) My company</Copyright>
</VersionInfo>
Predefined macros
| Macro name | Description |
|---|---|
$(Time) |
The current time at the start of the build, formatted as HH:mm. |
$(TimeExact) |
The current time at the start of the build, formatted as HH:mm:ss.ffff. |
$(Date) |
The current date. |
$(Year) |
The current year. |
$(CompilerDirectory) |
The path to the directory containing the Dassie Compiler executable. |
$(CompilerPath) |
The path to the Dassie Compiler executable (dc.dll). |
$(ProjectDir) |
The absolute path to the root directory of the current project. |
$(ProjectName) |
The name of the current project. |
$(OutputDir) |
The absolute path to the build output directory of the current project. |
Important
Be careful when using the $(Time) and $(TimeExact) macros inside build events. Since all macros are evaluated before the build starts, the value of these macros will stay the same between pre-build and post-build events. On Windows, you can use the %time% variable to accurately retrieve the current time instead.
Custom macros
Custom macros are contained in the <MacroDefinitions> tag. Here is an example of how to use them:
<MacroDefinitions>
<Define Macro="Author">My company</Define>
</MacroDefinitions>
<VersionInfo>
<Company>$(Author)</Company>
</VersionInfo>
Importing project files
The Import attribute can be used on the <DassieConfig> object to specify a configuration file to inherit settings from. When the compiler encounters this attribute, it loads the specified configuration file and applies all settings to the current configuration file. If the current file already contains a setting that is set by the imported configuration file, the inherited value is overwritten.
<!--measurements.xml-->
<DassieConfig>
<MeasureElapsedTime>true</MeasureElapsedTime>
</DassieConfig>
<!--dsconfig.xml-->
<DassieConfig Import="measurements.xml">
<ApplicationType>Library</ApplicationType>
<!--...-->
</DassieConfig>
Besides configuration files, the Import attribute also supports configuration providers from compiler extensions.
Transient Extensions
With transient extensions, projects can declare dependencies on Dassie compiler extensions. These extensions will then be active during the build process only. Additionally, the extension behavior can be customized with XML attributes and elements.
Transient extensions are declared in the <Extensions> tag, like in the following example:
<Extensions>
<Extension Path="./tools/Extension1.dll"/>
<Extension Path="./tools/Extension2.dll" CustomConfig="10"/>
</Extensions>
Important
Not every extension can be loaded in transient mode. Extension developers can customize which "loading modes" are supported.
For more information about compiler extensions, see Compiler Extensions.
Code Analysis Configuration
The <CodeAnalysis> element allows you to configure how the built-in code analyzer treats specific diagnostic messages:
<CodeAnalysis>
<Messages>
<Configure Code="DS0043" Severity="Error"/>
<Configure Code="DS0058" Severity="Warning"/>
<Configure Code="DS0070" Severity="Information"/>
</Messages>
</CodeAnalysis>
Message Severity Levels
| Severity | Description |
|---|---|
Information |
Informational message that does not affect compilation |
Warning |
Warning that may indicate a potential issue |
Error |
Error that prevents successful compilation |
Automatic Analysis
To automatically run code analyzers before every build:
<RunAnalyzers>true</RunAnalyzers>
Additional Settings
Maximum Errors
Stop compilation after a certain number of errors:
<MaxErrors>10</MaxErrors>
Setting this to 0 (default) allows unlimited errors.
Severity Indicators
Display icons in compiler output to distinguish message severity:
<EnableSeverityIndicators>true</EnableSeverityIndicators>
Document Sources
Configure document sources provided by compiler extensions:
<DocumentSources>
<Source Name="MyDocSource">
<Option>value</Option>
</Source>
</DocumentSources>
See Also
- Error Codes - Complete list of compiler error codes
- Compiler Extensions - Creating and using compiler extensions
- Project Groups - Multi-project solutions
- Command-Line Reference - Building and running projects