Coverage Report

Created: 2026-02-09 06:05

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/CMake/Source/cmTryCompileCommand.cxx
Line
Count
Source
1
/* Distributed under the OSI-approved BSD 3-Clause License.  See accompanying
2
   file LICENSE.rst or https://cmake.org/licensing for details.  */
3
#include "cmTryCompileCommand.h"
4
5
#include <cm/optional>
6
7
#include "cmConfigureLog.h"
8
#include "cmCoreTryCompile.h"
9
#include "cmExecutionStatus.h"
10
#include "cmMakefile.h"
11
#include "cmMessageType.h"
12
#include "cmRange.h"
13
#include "cmState.h"
14
#include "cmStateTypes.h"
15
#include "cmStringAlgorithms.h"
16
#include "cmValue.h"
17
#include "cmake.h"
18
19
namespace {
20
#ifndef CMAKE_BOOTSTRAP
21
void WriteTryCompileEvent(cmConfigureLog& log, cmMakefile const& mf,
22
                          cmTryCompileResult const& compileResult)
23
0
{
24
  // Keep in sync with cmFileAPIConfigureLog's DumpEventKindNames.
25
0
  static std::vector<unsigned int> const LogVersionsWithTryCompileV1{ 1 };
26
27
0
  if (log.IsAnyLogVersionEnabled(LogVersionsWithTryCompileV1)) {
28
0
    log.BeginEvent("try_compile-v1", mf);
29
0
    cmCoreTryCompile::WriteTryCompileEventFields(log, compileResult);
30
0
    log.EndEvent();
31
0
  }
32
0
}
33
#endif
34
}
35
36
bool cmTryCompileCommand(std::vector<std::string> const& args,
37
                         cmExecutionStatus& status)
38
0
{
39
0
  cmMakefile& mf = status.GetMakefile();
40
41
0
  if (args.size() < 3) {
42
0
    mf.IssueMessage(
43
0
      MessageType::FATAL_ERROR,
44
0
      "The try_compile() command requires at least 3 arguments.");
45
0
    return false;
46
0
  }
47
48
0
  if (mf.GetCMakeInstance()->GetState()->GetRole() ==
49
0
      cmState::Role::FindPackage) {
50
0
    mf.IssueMessage(
51
0
      MessageType::FATAL_ERROR,
52
0
      "The try_compile() command is not supported in --find-package mode.");
53
0
    return false;
54
0
  }
55
56
0
  cmStateEnums::TargetType targetType = cmStateEnums::EXECUTABLE;
57
0
  cmValue tt = mf.GetDefinition("CMAKE_TRY_COMPILE_TARGET_TYPE");
58
0
  if (cmNonempty(tt)) {
59
0
    if (*tt == cmState::GetTargetTypeName(cmStateEnums::EXECUTABLE)) {
60
0
      targetType = cmStateEnums::EXECUTABLE;
61
0
    } else if (*tt ==
62
0
               cmState::GetTargetTypeName(cmStateEnums::STATIC_LIBRARY)) {
63
0
      targetType = cmStateEnums::STATIC_LIBRARY;
64
0
    } else {
65
0
      mf.IssueMessage(
66
0
        MessageType::FATAL_ERROR,
67
0
        cmStrCat("Invalid value '", *tt,
68
0
                 "' for CMAKE_TRY_COMPILE_TARGET_TYPE.  Only '",
69
0
                 cmState::GetTargetTypeName(cmStateEnums::EXECUTABLE),
70
0
                 "' and '",
71
0
                 cmState::GetTargetTypeName(cmStateEnums::STATIC_LIBRARY),
72
0
                 "' are allowed."));
73
0
      return false;
74
0
    }
75
0
  }
76
77
0
  cmCoreTryCompile tc(&mf);
78
0
  cmCoreTryCompile::Arguments arguments =
79
0
    tc.ParseArgs(cmMakeRange(args), false);
80
0
  if (!arguments) {
81
0
    return true;
82
0
  }
83
84
0
  cm::optional<cmTryCompileResult> compileResult =
85
0
    tc.TryCompileCode(arguments, targetType);
86
0
#ifndef CMAKE_BOOTSTRAP
87
0
  if (compileResult && !arguments.NoLog) {
88
0
    if (cmConfigureLog* log = mf.GetCMakeInstance()->GetConfigureLog()) {
89
0
      WriteTryCompileEvent(*log, mf, *compileResult);
90
0
    }
91
0
  }
92
0
#endif
93
94
  // if They specified clean then we clean up what we can
95
0
  if (tc.SrcFileSignature) {
96
0
    if (!mf.GetCMakeInstance()->GetDebugTryCompile()) {
97
0
      tc.CleanupFiles(tc.BinaryDirectory);
98
0
    }
99
0
  }
100
0
  return true;
101
0
}