From e64fa5f1b611353522ec014192046ab3bf67e69f Mon Sep 17 00:00:00 2001
From: Vitaly Stakhovsky <vvs31415@gitlab.org>
Date: Tue, 14 Apr 2020 10:00:00 -0400
Subject: cmSourceFile::GetProperty: return cmProp

---
 Source/cmCPluginAPI.cxx                    |   3 +-
 Source/cmCommonTargetGenerator.cxx         |   4 +-
 Source/cmExtraSublimeTextGenerator.cxx     |  22 +++---
 Source/cmFileAPICodemodel.cxx              |   8 +-
 Source/cmGeneratorTarget.cxx               |  12 +--
 Source/cmGhsMultiTargetGenerator.cxx       |   8 +-
 Source/cmGlobalGenerator.cxx               |   4 +-
 Source/cmGlobalXCodeGenerator.cxx          |  33 +++++----
 Source/cmJsonObjects.cxx                   |  20 ++---
 Source/cmLocalGenerator.cxx                |  10 +--
 Source/cmLocalVisualStudio7Generator.cxx   |  27 +++----
 Source/cmMakefileTargetGenerator.cxx       |  28 +++----
 Source/cmNinjaTargetGenerator.cxx          |  36 ++++-----
 Source/cmQTWrapCPPCommand.cxx              |   3 +-
 Source/cmSourceFile.cxx                    |  34 ++++-----
 Source/cmSourceFile.h                      |   4 +-
 Source/cmVisualStudio10TargetGenerator.cxx | 114 +++++++++++++++--------------
 Source/cmVisualStudio10TargetGenerator.h   |   2 +-
 18 files changed, 191 insertions(+), 181 deletions(-)

diff --git a/Source/cmCPluginAPI.cxx b/Source/cmCPluginAPI.cxx
index 874efa5..697d435 100644
--- a/Source/cmCPluginAPI.cxx
+++ b/Source/cmCPluginAPI.cxx
@@ -580,7 +580,8 @@ const char* CCONV cmSourceFileGetProperty(void* arg, const char* prop)
 {
   cmCPluginAPISourceFile* sf = static_cast<cmCPluginAPISourceFile*>(arg);
   if (cmSourceFile* rsf = sf->RealSourceFile) {
-    return rsf->GetProperty(prop);
+    cmProp p = rsf->GetProperty(prop);
+    return p ? p->c_str() : nullptr;
   }
   if (!strcmp(prop, "LOCATION")) {
     return sf->FullPath.c_str();
diff --git a/Source/cmCommonTargetGenerator.cxx b/Source/cmCommonTargetGenerator.cxx
index 939f757..673936c 100644
--- a/Source/cmCommonTargetGenerator.cxx
+++ b/Source/cmCommonTargetGenerator.cxx
@@ -73,9 +73,9 @@ void cmCommonTargetGenerator::AddModuleDefinitionFlag(
 void cmCommonTargetGenerator::AppendFortranFormatFlags(
   std::string& flags, cmSourceFile const& source)
 {
-  const char* srcfmt = source.GetProperty("Fortran_FORMAT");
+  cmProp srcfmt = source.GetProperty("Fortran_FORMAT");
   cmOutputConverter::FortranFormat format =
-    cmOutputConverter::GetFortranFormat(srcfmt);
+    cmOutputConverter::GetFortranFormat(srcfmt ? srcfmt->c_str() : nullptr);
   if (format == cmOutputConverter::FortranFormatNone) {
     const char* tgtfmt = this->GeneratorTarget->GetProperty("Fortran_FORMAT");
     format = cmOutputConverter::GetFortranFormat(tgtfmt);
diff --git a/Source/cmExtraSublimeTextGenerator.cxx b/Source/cmExtraSublimeTextGenerator.cxx
index 5b136e2..6dbc7b7 100644
--- a/Source/cmExtraSublimeTextGenerator.cxx
+++ b/Source/cmExtraSublimeTextGenerator.cxx
@@ -23,6 +23,8 @@
 #include "cmSystemTools.h"
 #include "cmake.h"
 
+using cmProp = const std::string*; // just to silence IWYU
+
 /*
 Sublime Text 2 Generator
 Author: Morné Chamberlain
@@ -358,14 +360,14 @@ std::string cmExtraSublimeTextGenerator::ComputeFlagsForObject(
                                                     language);
 
   const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-  if (const char* cflags = source->GetProperty(COMPILE_FLAGS)) {
-    lg->AppendFlags(flags, genexInterpreter.Evaluate(cflags, COMPILE_FLAGS));
+  if (cmProp cflags = source->GetProperty(COMPILE_FLAGS)) {
+    lg->AppendFlags(flags, genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS));
   }
 
   const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-  if (const char* coptions = source->GetProperty(COMPILE_OPTIONS)) {
+  if (cmProp coptions = source->GetProperty(COMPILE_OPTIONS)) {
     lg->AppendCompileOptions(
-      flags, genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS));
+      flags, genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS));
   }
 
   return flags;
@@ -387,17 +389,17 @@ std::string cmExtraSublimeTextGenerator::ComputeDefines(
   // Add preprocessor definitions for this target and configuration.
   lg->GetTargetDefines(target, config, language, defines);
   const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
-  if (const char* compile_defs = source->GetProperty(COMPILE_DEFINITIONS)) {
+  if (cmProp compile_defs = source->GetProperty(COMPILE_DEFINITIONS)) {
     lg->AppendDefines(
-      defines, genexInterpreter.Evaluate(compile_defs, COMPILE_DEFINITIONS));
+      defines, genexInterpreter.Evaluate(*compile_defs, COMPILE_DEFINITIONS));
   }
 
   std::string defPropName =
     cmStrCat("COMPILE_DEFINITIONS_", cmSystemTools::UpperCase(config));
-  if (const char* config_compile_defs = source->GetProperty(defPropName)) {
+  if (cmProp config_compile_defs = source->GetProperty(defPropName)) {
     lg->AppendDefines(
       defines,
-      genexInterpreter.Evaluate(config_compile_defs, COMPILE_DEFINITIONS));
+      genexInterpreter.Evaluate(*config_compile_defs, COMPILE_DEFINITIONS));
   }
 
   std::string definesString;
@@ -419,9 +421,9 @@ std::string cmExtraSublimeTextGenerator::ComputeIncludes(
 
   // Add include directories for this source file
   const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-  if (const char* cincludes = source->GetProperty(INCLUDE_DIRECTORIES)) {
+  if (cmProp cincludes = source->GetProperty(INCLUDE_DIRECTORIES)) {
     lg->AppendIncludeDirectories(
-      includes, genexInterpreter.Evaluate(cincludes, INCLUDE_DIRECTORIES),
+      includes, genexInterpreter.Evaluate(*cincludes, INCLUDE_DIRECTORIES),
       *source);
   }
 
diff --git a/Source/cmFileAPICodemodel.cxx b/Source/cmFileAPICodemodel.cxx
index 70f5847..f4237cb 100644
--- a/Source/cmFileAPICodemodel.cxx
+++ b/Source/cmFileAPICodemodel.cxx
@@ -855,8 +855,8 @@ CompileData Target::BuildCompileData(cmSourceFile* sf)
                                                     fd.Language);
 
   const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-  if (const char* cflags = sf->GetProperty(COMPILE_FLAGS)) {
-    std::string flags = genexInterpreter.Evaluate(cflags, COMPILE_FLAGS);
+  if (cmProp cflags = sf->GetProperty(COMPILE_FLAGS)) {
+    std::string flags = genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS);
     fd.Flags.emplace_back(std::move(flags), JBTIndex());
   }
   const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
@@ -949,10 +949,10 @@ CompileData Target::BuildCompileData(cmSourceFile* sf)
   std::set<std::string> configFileDefines;
   const std::string defPropName =
     "COMPILE_DEFINITIONS_" + cmSystemTools::UpperCase(this->Config);
-  if (const char* config_defs = sf->GetProperty(defPropName)) {
+  if (cmProp config_defs = sf->GetProperty(defPropName)) {
     lg->AppendDefines(
       configFileDefines,
-      genexInterpreter.Evaluate(config_defs, COMPILE_DEFINITIONS));
+      genexInterpreter.Evaluate(*config_defs, COMPILE_DEFINITIONS));
   }
 
   fd.Defines.reserve(fileDefines.size() + configFileDefines.size());
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index 93eb8fb..55157b4 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -2839,8 +2839,8 @@ void cmTargetTraceDependencies::Trace()
     this->CurrentEntry = &this->GeneratorTarget->SourceDepends[sf];
 
     // Queue dependencies added explicitly by the user.
-    if (const char* additionalDeps = sf->GetProperty("OBJECT_DEPENDS")) {
-      std::vector<std::string> objDeps = cmExpandedList(additionalDeps);
+    if (cmProp additionalDeps = sf->GetProperty("OBJECT_DEPENDS")) {
+      std::vector<std::string> objDeps = cmExpandedList(*additionalDeps);
       for (std::string& objDep : objDeps) {
         if (cmSystemTools::FileIsFullPath(objDep)) {
           objDep = cmSystemTools::CollapseFullPath(objDep);
@@ -4707,16 +4707,16 @@ cmGeneratorTarget::GetTargetSourceFileFlags(const cmSourceFile* sf) const
   } else {
     // Handle the MACOSX_PACKAGE_LOCATION property on source files that
     // were not listed in one of the other lists.
-    if (const char* location = sf->GetProperty("MACOSX_PACKAGE_LOCATION")) {
-      flags.MacFolder = location;
+    if (cmProp location = sf->GetProperty("MACOSX_PACKAGE_LOCATION")) {
+      flags.MacFolder = location->c_str();
       const bool stripResources =
         this->GlobalGenerator->ShouldStripResourcePath(this->Makefile);
-      if (strcmp(location, "Resources") == 0) {
+      if (*location == "Resources") {
         flags.Type = cmGeneratorTarget::SourceFileTypeResource;
         if (stripResources) {
           flags.MacFolder = "";
         }
-      } else if (cmHasLiteralPrefix(location, "Resources/")) {
+      } else if (cmHasLiteralPrefix(*location, "Resources/")) {
         flags.Type = cmGeneratorTarget::SourceFileTypeDeepResource;
         if (stripResources) {
           flags.MacFolder += strlen("Resources/");
diff --git a/Source/cmGhsMultiTargetGenerator.cxx b/Source/cmGhsMultiTargetGenerator.cxx
index deb722f..f0c6d48 100644
--- a/Source/cmGhsMultiTargetGenerator.cxx
+++ b/Source/cmGhsMultiTargetGenerator.cxx
@@ -456,9 +456,9 @@ void cmGhsMultiTargetGenerator::WriteSourceProperty(
   std::ostream& fout, const cmSourceFile* sf, std::string const& propName,
   std::string const& propFlag)
 {
-  const char* prop = sf->GetProperty(propName);
+  cmProp prop = sf->GetProperty(propName);
   if (prop) {
-    std::vector<std::string> list = cmExpandedList(prop);
+    std::vector<std::string> list = cmExpandedList(*prop);
     for (const std::string& p : list) {
       fout << "    " << propFlag << p << '\n';
     }
@@ -708,9 +708,9 @@ void cmGhsMultiTargetGenerator::WriteCustomCommandLine(
 void cmGhsMultiTargetGenerator::WriteObjectLangOverride(
   std::ostream& fout, const cmSourceFile* sourceFile)
 {
-  const char* rawLangProp = sourceFile->GetProperty("LANGUAGE");
+  cmProp rawLangProp = sourceFile->GetProperty("LANGUAGE");
   if (nullptr != rawLangProp) {
-    std::string sourceLangProp(rawLangProp);
+    std::string sourceLangProp(*rawLangProp);
     std::string const& extension = sourceFile->GetExtension();
     if ("CXX" == sourceLangProp && ("c" == extension || "C" == extension)) {
       fout << "    -dotciscxx\n";
diff --git a/Source/cmGlobalGenerator.cxx b/Source/cmGlobalGenerator.cxx
index 4a6f6fb..4433a2c 100644
--- a/Source/cmGlobalGenerator.cxx
+++ b/Source/cmGlobalGenerator.cxx
@@ -3105,10 +3105,10 @@ void cmGlobalGenerator::WriteSummary(cmGeneratorTarget* target)
       std::string const& sfp = sf->ResolveFullPath();
       fout << sfp << "\n";
       lj_source["file"] = sfp;
-      if (const char* svalue = sf->GetProperty("LABELS")) {
+      if (cmProp svalue = sf->GetProperty("LABELS")) {
         labels.clear();
         Json::Value& lj_source_labels = lj_source["labels"] = Json::arrayValue;
-        cmExpandList(svalue, labels);
+        cmExpandList(*svalue, labels);
         for (std::string const& label : labels) {
           fout << " " << label << "\n";
           lj_source_labels.append(label);
diff --git a/Source/cmGlobalXCodeGenerator.cxx b/Source/cmGlobalXCodeGenerator.cxx
index 2191bc7..557cf7c 100644
--- a/Source/cmGlobalXCodeGenerator.cxx
+++ b/Source/cmGlobalXCodeGenerator.cxx
@@ -809,8 +809,9 @@ cmXCodeObject* cmGlobalXCodeGenerator::CreateXCodeSourceFile(
 
   // Add flags from target and source file properties.
   std::string flags;
-  const char* srcfmt = sf->GetProperty("Fortran_FORMAT");
-  switch (cmOutputConverter::GetFortranFormat(srcfmt)) {
+  cmProp srcfmt = sf->GetProperty("Fortran_FORMAT");
+  switch (
+    cmOutputConverter::GetFortranFormat(srcfmt ? srcfmt->c_str() : nullptr)) {
     case cmOutputConverter::FortranFormatFixed:
       flags = "-fixed " + flags;
       break;
@@ -821,22 +822,22 @@ cmXCodeObject* cmGlobalXCodeGenerator::CreateXCodeSourceFile(
       break;
   }
   const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-  if (const char* cflags = sf->GetProperty(COMPILE_FLAGS)) {
-    lg->AppendFlags(flags, genexInterpreter.Evaluate(cflags, COMPILE_FLAGS));
+  if (cmProp cflags = sf->GetProperty(COMPILE_FLAGS)) {
+    lg->AppendFlags(flags, genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS));
   }
   const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-  if (const char* coptions = sf->GetProperty(COMPILE_OPTIONS)) {
+  if (cmProp coptions = sf->GetProperty(COMPILE_OPTIONS)) {
     lg->AppendCompileOptions(
-      flags, genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS));
+      flags, genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS));
   }
 
   // Add per-source definitions.
   BuildObjectListOrString flagsBuild(this, false);
   const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
-  if (const char* compile_defs = sf->GetProperty(COMPILE_DEFINITIONS)) {
+  if (cmProp compile_defs = sf->GetProperty(COMPILE_DEFINITIONS)) {
     this->AppendDefines(
       flagsBuild,
-      genexInterpreter.Evaluate(compile_defs, COMPILE_DEFINITIONS).c_str(),
+      genexInterpreter.Evaluate(*compile_defs, COMPILE_DEFINITIONS).c_str(),
       true);
   }
 
@@ -854,9 +855,9 @@ cmXCodeObject* cmGlobalXCodeGenerator::CreateXCodeSourceFile(
   // Add per-source include directories.
   std::vector<std::string> includes;
   const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-  if (const char* cincludes = sf->GetProperty(INCLUDE_DIRECTORIES)) {
+  if (cmProp cincludes = sf->GetProperty(INCLUDE_DIRECTORIES)) {
     lg->AppendIncludeDirectories(
-      includes, genexInterpreter.Evaluate(cincludes, INCLUDE_DIRECTORIES),
+      includes, genexInterpreter.Evaluate(*cincludes, INCLUDE_DIRECTORIES),
       *sf);
   }
   lg->AppendFlags(flags, lg->GetIncludeFlags(includes, gtgt, lang, true));
@@ -885,10 +886,10 @@ cmXCodeObject* cmGlobalXCodeGenerator::CreateXCodeSourceFile(
   }
 
   // Add user-specified file attributes.
-  const char* extraFileAttributes = sf->GetProperty("XCODE_FILE_ATTRIBUTES");
+  cmProp extraFileAttributes = sf->GetProperty("XCODE_FILE_ATTRIBUTES");
   if (extraFileAttributes) {
     // Expand the list of attributes.
-    std::vector<std::string> attributes = cmExpandedList(extraFileAttributes);
+    std::vector<std::string> attributes = cmExpandedList(*extraFileAttributes);
 
     // Store the attributes.
     for (const auto& attribute : attributes) {
@@ -999,11 +1000,11 @@ cmXCodeObject* cmGlobalXCodeGenerator::CreateXCodeFileReferenceFromPath(
   bool useLastKnownFileType = false;
   std::string fileType;
   if (sf) {
-    if (const char* e = sf->GetProperty("XCODE_EXPLICIT_FILE_TYPE")) {
-      fileType = e;
-    } else if (const char* l = sf->GetProperty("XCODE_LAST_KNOWN_FILE_TYPE")) {
+    if (cmProp e = sf->GetProperty("XCODE_EXPLICIT_FILE_TYPE")) {
+      fileType = *e;
+    } else if (cmProp l = sf->GetProperty("XCODE_LAST_KNOWN_FILE_TYPE")) {
       useLastKnownFileType = true;
-      fileType = l;
+      fileType = *l;
     }
   }
   if (fileType.empty()) {
diff --git a/Source/cmJsonObjects.cxx b/Source/cmJsonObjects.cxx
index 9ecf378..a4f78bc 100644
--- a/Source/cmJsonObjects.cxx
+++ b/Source/cmJsonObjects.cxx
@@ -275,14 +275,14 @@ static Json::Value DumpSourceFilesList(
 
       std::string compileFlags = ld.Flags;
       const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-      if (const char* cflags = file->GetProperty(COMPILE_FLAGS)) {
+      if (cmProp cflags = file->GetProperty(COMPILE_FLAGS)) {
         lg->AppendFlags(compileFlags,
-                        genexInterpreter.Evaluate(cflags, COMPILE_FLAGS));
+                        genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS));
       }
       const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-      if (const char* coptions = file->GetProperty(COMPILE_OPTIONS)) {
+      if (cmProp coptions = file->GetProperty(COMPILE_OPTIONS)) {
         lg->AppendCompileOptions(
-          compileFlags, genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS));
+          compileFlags, genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS));
       }
       fileData.Flags = compileFlags;
 
@@ -290,9 +290,9 @@ static Json::Value DumpSourceFilesList(
       std::vector<std::string> includes;
 
       const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-      if (const char* cincludes = file->GetProperty(INCLUDE_DIRECTORIES)) {
+      if (cmProp cincludes = file->GetProperty(INCLUDE_DIRECTORIES)) {
         const std::string& evaluatedIncludes =
-          genexInterpreter.Evaluate(cincludes, INCLUDE_DIRECTORIES);
+          genexInterpreter.Evaluate(*cincludes, INCLUDE_DIRECTORIES);
         lg->AppendIncludeDirectories(includes, evaluatedIncludes, *file);
 
         for (const auto& include : includes) {
@@ -309,17 +309,17 @@ static Json::Value DumpSourceFilesList(
 
       const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
       std::set<std::string> defines;
-      if (const char* defs = file->GetProperty(COMPILE_DEFINITIONS)) {
+      if (cmProp defs = file->GetProperty(COMPILE_DEFINITIONS)) {
         lg->AppendDefines(
-          defines, genexInterpreter.Evaluate(defs, COMPILE_DEFINITIONS));
+          defines, genexInterpreter.Evaluate(*defs, COMPILE_DEFINITIONS));
       }
 
       const std::string defPropName =
         "COMPILE_DEFINITIONS_" + cmSystemTools::UpperCase(config);
-      if (const char* config_defs = file->GetProperty(defPropName)) {
+      if (cmProp config_defs = file->GetProperty(defPropName)) {
         lg->AppendDefines(
           defines,
-          genexInterpreter.Evaluate(config_defs, COMPILE_DEFINITIONS));
+          genexInterpreter.Evaluate(*config_defs, COMPILE_DEFINITIONS));
       }
 
       defines.insert(ld.Defines.begin(), ld.Defines.end());
diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx
index e6083d3..9323404 100644
--- a/Source/cmLocalGenerator.cxx
+++ b/Source/cmLocalGenerator.cxx
@@ -3410,12 +3410,12 @@ std::string cmLocalGenerator::GetObjectFileNameWithoutTarget(
   // Ensure that for the CMakeFiles/<target>.dir/generated_source_file
   // we don't end up having:
   // CMakeFiles/<target>.dir/CMakeFiles/<target>.dir/generated_source_file.obj
-  const char* unitySourceFile = source.GetProperty("UNITY_SOURCE_FILE");
-  const char* pchExtension = source.GetProperty("PCH_EXTENSION");
+  cmProp unitySourceFile = source.GetProperty("UNITY_SOURCE_FILE");
+  cmProp psExtension = source.GetProperty("PCH_EXTENSION");
   const bool isPchObject = objectName.find("cmake_pch") != std::string::npos;
-  if (unitySourceFile || pchExtension || isPchObject) {
-    if (pchExtension) {
-      customOutputExtension = pchExtension;
+  if (unitySourceFile || psExtension || isPchObject) {
+    if (psExtension) {
+      customOutputExtension = psExtension->c_str();
     }
 
     cmsys::RegularExpression var("(CMakeFiles/[^/]+.dir/)");
diff --git a/Source/cmLocalVisualStudio7Generator.cxx b/Source/cmLocalVisualStudio7Generator.cxx
index 9148b27..0a58367 100644
--- a/Source/cmLocalVisualStudio7Generator.cxx
+++ b/Source/cmLocalVisualStudio7Generator.cxx
@@ -1445,14 +1445,15 @@ cmLocalVisualStudio7GeneratorFCInfo::cmLocalVisualStudio7GeneratorFCInfo(
       needfc = true;
     }
     const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-    if (const char* cflags = sf.GetProperty(COMPILE_FLAGS)) {
-      fc.CompileFlags = genexInterpreter.Evaluate(cflags, COMPILE_FLAGS);
+    if (cmProp cflags = sf.GetProperty(COMPILE_FLAGS)) {
+      fc.CompileFlags = genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS);
       needfc = true;
     }
     const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-    if (const char* coptions = sf.GetProperty(COMPILE_OPTIONS)) {
+    if (cmProp coptions = sf.GetProperty(COMPILE_OPTIONS)) {
       lg->AppendCompileOptions(
-        fc.CompileFlags, genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS));
+        fc.CompileFlags,
+        genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS));
       needfc = true;
     }
     // Add precompile headers compile options.
@@ -1473,7 +1474,7 @@ cmLocalVisualStudio7GeneratorFCInfo::cmLocalVisualStudio7GeneratorFCInfo(
 
     if (lg->FortranProject) {
       switch (cmOutputConverter::GetFortranFormat(
-        sf.GetProperty("Fortran_FORMAT"))) {
+        sf.GetSafeProperty("Fortran_FORMAT"))) {
         case cmOutputConverter::FortranFormatFixed:
           fc.CompileFlags = "-fixed " + fc.CompileFlags;
           needfc = true;
@@ -1487,26 +1488,26 @@ cmLocalVisualStudio7GeneratorFCInfo::cmLocalVisualStudio7GeneratorFCInfo(
       }
     }
     const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
-    if (const char* cdefs = sf.GetProperty(COMPILE_DEFINITIONS)) {
-      fc.CompileDefs = genexInterpreter.Evaluate(cdefs, COMPILE_DEFINITIONS);
+    if (cmProp cdefs = sf.GetProperty(COMPILE_DEFINITIONS)) {
+      fc.CompileDefs = genexInterpreter.Evaluate(*cdefs, COMPILE_DEFINITIONS);
       needfc = true;
     }
     std::string defPropName = cmStrCat("COMPILE_DEFINITIONS_", configUpper);
-    if (const char* ccdefs = sf.GetProperty(defPropName)) {
+    if (cmProp ccdefs = sf.GetProperty(defPropName)) {
       fc.CompileDefsConfig =
-        genexInterpreter.Evaluate(ccdefs, COMPILE_DEFINITIONS);
+        genexInterpreter.Evaluate(*ccdefs, COMPILE_DEFINITIONS);
       needfc = true;
     }
 
     const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-    if (const char* cincs = sf.GetProperty(INCLUDE_DIRECTORIES)) {
-      fc.IncludeDirs = genexInterpreter.Evaluate(cincs, INCLUDE_DIRECTORIES);
+    if (cmProp cincs = sf.GetProperty(INCLUDE_DIRECTORIES)) {
+      fc.IncludeDirs = genexInterpreter.Evaluate(*cincs, INCLUDE_DIRECTORIES);
       needfc = true;
     }
 
     // Check for extra object-file dependencies.
-    if (const char* deps = sf.GetProperty("OBJECT_DEPENDS")) {
-      std::vector<std::string> depends = cmExpandedList(deps);
+    if (cmProp deps = sf.GetProperty("OBJECT_DEPENDS")) {
+      std::vector<std::string> depends = cmExpandedList(*deps);
       const char* sep = "";
       for (const std::string& d : depends) {
         fc.AdditionalDeps += sep;
diff --git a/Source/cmMakefileTargetGenerator.cxx b/Source/cmMakefileTargetGenerator.cxx
index 5bb4c57..2d8f8d6 100644
--- a/Source/cmMakefileTargetGenerator.cxx
+++ b/Source/cmMakefileTargetGenerator.cxx
@@ -527,9 +527,9 @@ void cmMakefileTargetGenerator::WriteObjectRuleFiles(
 
   // Add flags from source file properties.
   const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-  if (const char* cflags = source.GetProperty(COMPILE_FLAGS)) {
+  if (cmProp cflags = source.GetProperty(COMPILE_FLAGS)) {
     const std::string& evaluatedFlags =
-      genexInterpreter.Evaluate(cflags, COMPILE_FLAGS);
+      genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS);
     this->LocalGenerator->AppendFlags(flags, evaluatedFlags);
     *this->FlagFileStream << "# Custom flags: " << relativeObj
                           << "_FLAGS = " << evaluatedFlags << "\n"
@@ -537,9 +537,9 @@ void cmMakefileTargetGenerator::WriteObjectRuleFiles(
   }
 
   const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-  if (const char* coptions = source.GetProperty(COMPILE_OPTIONS)) {
+  if (cmProp coptions = source.GetProperty(COMPILE_OPTIONS)) {
     const std::string& evaluatedOptions =
-      genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS);
+      genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS);
     this->LocalGenerator->AppendCompileOptions(flags, evaluatedOptions);
     *this->FlagFileStream << "# Custom options: " << relativeObj
                           << "_OPTIONS = " << evaluatedOptions << "\n"
@@ -571,9 +571,9 @@ void cmMakefileTargetGenerator::WriteObjectRuleFiles(
   std::vector<std::string> includes;
 
   const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-  if (const char* cincludes = source.GetProperty(INCLUDE_DIRECTORIES)) {
+  if (cmProp cincludes = source.GetProperty(INCLUDE_DIRECTORIES)) {
     const std::string& evaluatedIncludes =
-      genexInterpreter.Evaluate(cincludes, INCLUDE_DIRECTORIES);
+      genexInterpreter.Evaluate(*cincludes, INCLUDE_DIRECTORIES);
     this->LocalGenerator->AppendIncludeDirectories(includes, evaluatedIncludes,
                                                    source);
     *this->FlagFileStream << "# Custom include directories: " << relativeObj
@@ -587,18 +587,18 @@ void cmMakefileTargetGenerator::WriteObjectRuleFiles(
 
   // Add source-specific preprocessor definitions.
   const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
-  if (const char* compile_defs = source.GetProperty(COMPILE_DEFINITIONS)) {
+  if (cmProp compile_defs = source.GetProperty(COMPILE_DEFINITIONS)) {
     const std::string& evaluatedDefs =
-      genexInterpreter.Evaluate(compile_defs, COMPILE_DEFINITIONS);
+      genexInterpreter.Evaluate(*compile_defs, COMPILE_DEFINITIONS);
     this->LocalGenerator->AppendDefines(defines, evaluatedDefs);
     *this->FlagFileStream << "# Custom defines: " << relativeObj
                           << "_DEFINES = " << evaluatedDefs << "\n"
                           << "\n";
   }
   std::string defPropName = cmStrCat("COMPILE_DEFINITIONS_", configUpper);
-  if (const char* config_compile_defs = source.GetProperty(defPropName)) {
+  if (cmProp config_compile_defs = source.GetProperty(defPropName)) {
     const std::string& evaluatedDefs =
-      genexInterpreter.Evaluate(config_compile_defs, COMPILE_DEFINITIONS);
+      genexInterpreter.Evaluate(*config_compile_defs, COMPILE_DEFINITIONS);
     this->LocalGenerator->AppendDefines(defines, evaluatedDefs);
     *this->FlagFileStream << "# Custom defines: " << relativeObj << "_DEFINES_"
                           << configUpper << " = " << evaluatedDefs << "\n"
@@ -876,9 +876,9 @@ void cmMakefileTargetGenerator::WriteObjectRuleFiles(
 
   // Check for extra outputs created by the compilation.
   std::vector<std::string> outputs(1, relativeObj);
-  if (const char* extra_outputs_str = source.GetProperty("OBJECT_OUTPUTS")) {
+  if (cmProp extra_outputs_str = source.GetProperty("OBJECT_OUTPUTS")) {
     // Register these as extra files to clean.
-    cmExpandList(extra_outputs_str, outputs);
+    cmExpandList(*extra_outputs_str, outputs);
     this->CleanFiles.insert(outputs.begin() + 1, outputs.end());
   }
 
@@ -1229,8 +1229,8 @@ void cmMakefileTargetGenerator::WriteObjectDependRules(
   // Create the list of dependencies known at cmake time.  These are
   // shared between the object file and dependency scanning rule.
   depends.push_back(source.GetFullPath());
-  if (const char* objectDeps = source.GetProperty("OBJECT_DEPENDS")) {
-    cmExpandList(objectDeps, depends);
+  if (cmProp objectDeps = source.GetProperty("OBJECT_DEPENDS")) {
+    cmExpandList(*objectDeps, depends);
   }
 }
 
diff --git a/Source/cmNinjaTargetGenerator.cxx b/Source/cmNinjaTargetGenerator.cxx
index ed74cf9..a70b6a0 100644
--- a/Source/cmNinjaTargetGenerator.cxx
+++ b/Source/cmNinjaTargetGenerator.cxx
@@ -190,15 +190,15 @@ std::string cmNinjaTargetGenerator::ComputeFlagsForObject(
     this->LocalGenerator, config, this->GeneratorTarget, language);
 
   const std::string COMPILE_FLAGS("COMPILE_FLAGS");
-  if (const char* cflags = source->GetProperty(COMPILE_FLAGS)) {
+  if (cmProp cflags = source->GetProperty(COMPILE_FLAGS)) {
     this->LocalGenerator->AppendFlags(
-      flags, genexInterpreter.Evaluate(cflags, COMPILE_FLAGS));
+      flags, genexInterpreter.Evaluate(*cflags, COMPILE_FLAGS));
   }
 
   const std::string COMPILE_OPTIONS("COMPILE_OPTIONS");
-  if (const char* coptions = source->GetProperty(COMPILE_OPTIONS)) {
+  if (cmProp coptions = source->GetProperty(COMPILE_OPTIONS)) {
     this->LocalGenerator->AppendCompileOptions(
-      flags, genexInterpreter.Evaluate(coptions, COMPILE_OPTIONS));
+      flags, genexInterpreter.Evaluate(*coptions, COMPILE_OPTIONS));
   }
 
   // Add precompile headers compile options.
@@ -281,17 +281,17 @@ std::string cmNinjaTargetGenerator::ComputeDefines(cmSourceFile const* source,
   }
 
   const std::string COMPILE_DEFINITIONS("COMPILE_DEFINITIONS");
-  if (const char* compile_defs = source->GetProperty(COMPILE_DEFINITIONS)) {
+  if (cmProp compile_defs = source->GetProperty(COMPILE_DEFINITIONS)) {
     this->LocalGenerator->AppendDefines(
-      defines, genexInterpreter.Evaluate(compile_defs, COMPILE_DEFINITIONS));
+      defines, genexInterpreter.Evaluate(*compile_defs, COMPILE_DEFINITIONS));
   }
 
   std::string defPropName =
     cmStrCat("COMPILE_DEFINITIONS_", cmSystemTools::UpperCase(config));
-  if (const char* config_compile_defs = source->GetProperty(defPropName)) {
+  if (cmProp config_compile_defs = source->GetProperty(defPropName)) {
     this->LocalGenerator->AppendDefines(
       defines,
-      genexInterpreter.Evaluate(config_compile_defs, COMPILE_DEFINITIONS));
+      genexInterpreter.Evaluate(*config_compile_defs, COMPILE_DEFINITIONS));
   }
 
   std::string definesString = this->GetDefines(language, config);
@@ -309,9 +309,9 @@ std::string cmNinjaTargetGenerator::ComputeIncludes(
     this->LocalGenerator, config, this->GeneratorTarget, language);
 
   const std::string INCLUDE_DIRECTORIES("INCLUDE_DIRECTORIES");
-  if (const char* cincludes = source->GetProperty(INCLUDE_DIRECTORIES)) {
+  if (cmProp cincludes = source->GetProperty(INCLUDE_DIRECTORIES)) {
     this->LocalGenerator->AppendIncludeDirectories(
-      includes, genexInterpreter.Evaluate(cincludes, INCLUDE_DIRECTORIES),
+      includes, genexInterpreter.Evaluate(*cincludes, INCLUDE_DIRECTORIES),
       *source);
   }
 
@@ -1096,8 +1096,8 @@ void cmNinjaTargetGenerator::WriteObjectBuildStatement(
     }
   }
 
-  if (const char* objectDeps = source->GetProperty("OBJECT_DEPENDS")) {
-    std::vector<std::string> objDepList = cmExpandedList(objectDeps);
+  if (cmProp objectDeps = source->GetProperty("OBJECT_DEPENDS")) {
+    std::vector<std::string> objDepList = cmExpandedList(*objectDeps);
     std::copy(objDepList.begin(), objDepList.end(),
               std::back_inserter(depList));
   }
@@ -1264,10 +1264,10 @@ void cmNinjaTargetGenerator::WriteObjectBuildStatement(
                                            objBuild, commandLineLengthLimit);
   }
 
-  if (const char* objectOutputs = source->GetProperty("OBJECT_OUTPUTS")) {
+  if (cmProp objectOutputs = source->GetProperty("OBJECT_OUTPUTS")) {
     cmNinjaBuild build("phony");
     build.Comment = "Additional output files.";
-    build.Outputs = cmExpandedList(objectOutputs);
+    build.Outputs = cmExpandedList(*objectOutputs);
     std::transform(build.Outputs.begin(), build.Outputs.end(),
                    build.Outputs.begin(), MapToNinjaPath());
     build.ExplicitDeps = objBuild.Outputs;
@@ -1331,14 +1331,14 @@ void cmNinjaTargetGenerator::EmitSwiftDependencyInfo(
   std::string const objectFilePath =
     this->ConvertToNinjaPath(this->GetObjectFilePath(source, config));
   std::string const swiftDepsPath = [source, objectFilePath]() -> std::string {
-    if (const char* name = source->GetProperty("Swift_DEPENDENCIES_FILE")) {
-      return name;
+    if (cmProp name = source->GetProperty("Swift_DEPENDENCIES_FILE")) {
+      return *name;
     }
     return cmStrCat(objectFilePath, ".swiftdeps");
   }();
   std::string const swiftDiaPath = [source, objectFilePath]() -> std::string {
-    if (const char* name = source->GetProperty("Swift_DIAGNOSTICS_FILE")) {
-      return name;
+    if (cmProp name = source->GetProperty("Swift_DIAGNOSTICS_FILE")) {
+      return *name;
     }
     return cmStrCat(objectFilePath, ".dia");
   }();
diff --git a/Source/cmQTWrapCPPCommand.cxx b/Source/cmQTWrapCPPCommand.cxx
index cc4df8f..48c4b10 100644
--- a/Source/cmQTWrapCPPCommand.cxx
+++ b/Source/cmQTWrapCPPCommand.cxx
@@ -39,7 +39,8 @@ bool cmQTWrapCPPCommand(std::vector<std::string> const& args,
         cmStrCat(mf.GetCurrentBinaryDirectory(), "/moc_", srcName, ".cxx");
       cmSourceFile* sf = mf.GetOrCreateSource(newName, true);
       if (curr) {
-        sf->SetProperty("ABSTRACT", curr->GetProperty("ABSTRACT"));
+        cmProp p = curr->GetProperty("ABSTRACT");
+        sf->SetProperty("ABSTRACT", p ? p->c_str() : nullptr);
       }
 
       // Compute the name of the header from which to generate the file.
diff --git a/Source/cmSourceFile.cxx b/Source/cmSourceFile.cxx
index ad59cd6..f525439 100644
--- a/Source/cmSourceFile.cxx
+++ b/Source/cmSourceFile.cxx
@@ -48,9 +48,9 @@ std::string cmSourceFile::GetObjectLibrary() const
 std::string const& cmSourceFile::GetOrDetermineLanguage()
 {
   // If the language was set explicitly by the user then use it.
-  if (const char* lang = this->GetProperty(propLANGUAGE)) {
+  if (cmProp lang = this->GetProperty(propLANGUAGE)) {
     // Assign to member in order to return a reference.
-    this->Language = lang;
+    this->Language = *lang;
     return this->Language;
   }
 
@@ -81,8 +81,8 @@ std::string const& cmSourceFile::GetOrDetermineLanguage()
 std::string cmSourceFile::GetLanguage() const
 {
   // If the language was set explicitly by the user then use it.
-  if (const char* lang = this->GetProperty(propLANGUAGE)) {
-    return lang;
+  if (cmProp lang = this->GetProperty(propLANGUAGE)) {
+    return *lang;
   }
 
   // Use the language determined from the file extension.
@@ -317,17 +317,18 @@ const char* cmSourceFile::GetPropertyForUser(const std::string& prop)
   }
 
   // Perform the normal property lookup.
-  return this->GetProperty(prop);
+  cmProp p = this->GetProperty(prop);
+  return p ? p->c_str() : nullptr;
 }
 
-const char* cmSourceFile::GetProperty(const std::string& prop) const
+cmProp cmSourceFile::GetProperty(const std::string& prop) const
 {
   // Check for computed properties.
   if (prop == propLOCATION) {
     if (this->FullPath.empty()) {
       return nullptr;
     }
-    return this->FullPath.c_str();
+    return &this->FullPath;
   }
 
   // Check for the properties with backtraces.
@@ -338,7 +339,7 @@ const char* cmSourceFile::GetProperty(const std::string& prop) const
 
     static std::string output;
     output = cmJoin(this->IncludeDirectories, ";");
-    return output.c_str();
+    return &output;
   }
 
   if (prop == propCOMPILE_OPTIONS) {
@@ -348,7 +349,7 @@ const char* cmSourceFile::GetProperty(const std::string& prop) const
 
     static std::string output;
     output = cmJoin(this->CompileOptions, ";");
-    return output.c_str();
+    return &output;
   }
 
   if (prop == propCOMPILE_DEFINITIONS) {
@@ -358,7 +359,7 @@ const char* cmSourceFile::GetProperty(const std::string& prop) const
 
     static std::string output;
     output = cmJoin(this->CompileDefinitions, ";");
-    return output.c_str();
+    return &output;
   }
 
   cmProp retVal = this->Properties.GetPropertyValue(prop);
@@ -367,28 +368,27 @@ const char* cmSourceFile::GetProperty(const std::string& prop) const
     const bool chain =
       mf->GetState()->IsPropertyChained(prop, cmProperty::SOURCE_FILE);
     if (chain) {
-      if (cmProp p = mf->GetProperty(prop, chain)) {
-        return p->c_str();
-      }
+      return mf->GetProperty(prop, chain);
     }
     return nullptr;
   }
 
-  return retVal->c_str();
+  return retVal;
 }
 
 const char* cmSourceFile::GetSafeProperty(const std::string& prop) const
 {
-  const char* ret = this->GetProperty(prop);
+  cmProp ret = this->GetProperty(prop);
   if (!ret) {
     return "";
   }
-  return ret;
+  return ret->c_str();
 }
 
 bool cmSourceFile::GetPropertyAsBool(const std::string& prop) const
 {
-  return cmIsOn(this->GetProperty(prop));
+  cmProp p = this->GetProperty(prop);
+  return p && cmIsOn(*p);
 }
 
 void cmSourceFile::SetProperties(cmPropertyMap properties)
diff --git a/Source/cmSourceFile.h b/Source/cmSourceFile.h
index e22829f..e527069 100644
--- a/Source/cmSourceFile.h
+++ b/Source/cmSourceFile.h
@@ -17,6 +17,8 @@
 
 class cmMakefile;
 
+using cmProp = const std::string*;
+
 /** \class cmSourceFile
  * \brief Represent a class loaded from a makefile.
  *
@@ -45,7 +47,7 @@ public:
   void AppendProperty(const std::string& prop, const std::string& value,
                       bool asString = false);
   //! Might return a nullptr if the property is not set or invalid
-  const char* GetProperty(const std::string& prop) const;
+  cmProp GetProperty(const std::string& prop) const;
   //! Always returns a valid pointer
   const char* GetSafeProperty(const std::string& prop) const;
   bool GetPropertyAsBool(const std::string& prop) const;
diff --git a/Source/cmVisualStudio10TargetGenerator.cxx b/Source/cmVisualStudio10TargetGenerator.cxx
index ec7fe96..07c477e 100644
--- a/Source/cmVisualStudio10TargetGenerator.cxx
+++ b/Source/cmVisualStudio10TargetGenerator.cxx
@@ -983,8 +983,8 @@ void cmVisualStudio10TargetGenerator::WriteEmbeddedResourceGroup(Elem& e0)
           ".Designer.cs";
         if (cmsys::SystemTools::FileExists(designerResource)) {
           std::string generator = "PublicResXFileCodeGenerator";
-          if (const char* g = oi->GetProperty("VS_RESOURCE_GENERATOR")) {
-            generator = g;
+          if (cmProp g = oi->GetProperty("VS_RESOURCE_GENERATOR")) {
+            generator = *g;
           }
           if (!generator.empty()) {
             e2.Element("Generator", generator);
@@ -1027,10 +1027,10 @@ void cmVisualStudio10TargetGenerator::WriteXamlFilesGroup(Elem& e0)
     Elem e1(e0, "ItemGroup");
     for (cmSourceFile const* oi : xamlObjs) {
       std::string obj = oi->GetFullPath();
-      const char* xamlType;
-      const char* xamlTypeProperty = oi->GetProperty("VS_XAML_TYPE");
+      std::string xamlType;
+      cmProp xamlTypeProperty = oi->GetProperty("VS_XAML_TYPE");
       if (xamlTypeProperty) {
-        xamlType = xamlTypeProperty;
+        xamlType = *xamlTypeProperty;
       } else {
         xamlType = "Page";
       }
@@ -1745,9 +1745,9 @@ void cmVisualStudio10TargetGenerator::WriteHeaderSource(Elem& e1,
 }
 
 void cmVisualStudio10TargetGenerator::ParseSettingsProperty(
-  const char* settingsPropertyValue, ConfigToSettings& toolSettings)
+  const std::string& settingsPropertyValue, ConfigToSettings& toolSettings)
 {
-  if (settingsPropertyValue) {
+  if (!settingsPropertyValue.empty()) {
     cmGeneratorExpression ge;
 
     std::unique_ptr<cmCompiledGeneratorExpression> cge =
@@ -1821,45 +1821,45 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
   if (ext == "hlsl") {
     tool = "FXCompile";
     // Figure out the type of shader compiler to use.
-    if (const char* st = sf->GetProperty("VS_SHADER_TYPE")) {
+    if (cmProp st = sf->GetProperty("VS_SHADER_TYPE")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["ShaderType"] = st;
+        toolSettings[config]["ShaderType"] = *st;
       }
     }
     // Figure out which entry point to use if any
-    if (const char* se = sf->GetProperty("VS_SHADER_ENTRYPOINT")) {
+    if (cmProp se = sf->GetProperty("VS_SHADER_ENTRYPOINT")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["EntryPointName"] = se;
+        toolSettings[config]["EntryPointName"] = *se;
       }
     }
     // Figure out which shader model to use if any
-    if (const char* sm = sf->GetProperty("VS_SHADER_MODEL")) {
+    if (cmProp sm = sf->GetProperty("VS_SHADER_MODEL")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["ShaderModel"] = sm;
+        toolSettings[config]["ShaderModel"] = *sm;
       }
     }
     // Figure out which output header file to use if any
-    if (const char* ohf = sf->GetProperty("VS_SHADER_OUTPUT_HEADER_FILE")) {
+    if (cmProp ohf = sf->GetProperty("VS_SHADER_OUTPUT_HEADER_FILE")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["HeaderFileOutput"] = ohf;
+        toolSettings[config]["HeaderFileOutput"] = *ohf;
       }
     }
     // Figure out which variable name to use if any
-    if (const char* vn = sf->GetProperty("VS_SHADER_VARIABLE_NAME")) {
+    if (cmProp vn = sf->GetProperty("VS_SHADER_VARIABLE_NAME")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["VariableName"] = vn;
+        toolSettings[config]["VariableName"] = *vn;
       }
     }
     // Figure out if there's any additional flags to use
-    if (const char* saf = sf->GetProperty("VS_SHADER_FLAGS")) {
+    if (cmProp saf = sf->GetProperty("VS_SHADER_FLAGS")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["AdditionalOptions"] = saf;
+        toolSettings[config]["AdditionalOptions"] = *saf;
       }
     }
     // Figure out if debug information should be generated
-    if (const char* sed = sf->GetProperty("VS_SHADER_ENABLE_DEBUG")) {
+    if (cmProp sed = sf->GetProperty("VS_SHADER_ENABLE_DEBUG")) {
       cmGeneratorExpression ge;
-      std::unique_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(sed);
+      std::unique_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(*sed);
 
       for (const std::string& config : this->Configurations) {
         std::string evaluated = cge->Evaluate(this->LocalGenerator, config);
@@ -1871,9 +1871,9 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
       }
     }
     // Figure out if optimizations should be disabled
-    if (const char* sdo = sf->GetProperty("VS_SHADER_DISABLE_OPTIMIZATIONS")) {
+    if (cmProp sdo = sf->GetProperty("VS_SHADER_DISABLE_OPTIMIZATIONS")) {
       cmGeneratorExpression ge;
-      std::unique_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(sdo);
+      std::unique_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(*sdo);
 
       for (const std::string& config : this->Configurations) {
         std::string evaluated = cge->Evaluate(this->LocalGenerator, config);
@@ -1884,9 +1884,9 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
         }
       }
     }
-    if (const char* sofn = sf->GetProperty("VS_SHADER_OBJECT_FILE_NAME")) {
+    if (cmProp sofn = sf->GetProperty("VS_SHADER_OBJECT_FILE_NAME")) {
       for (const std::string& config : this->Configurations) {
-        toolSettings[config]["ObjectFileOutput"] = sofn;
+        toolSettings[config]["ObjectFileOutput"] = *sofn;
       }
     }
   } else if (ext == "jpg" || ext == "png") {
@@ -1907,9 +1907,9 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
   } else if (ext == "vsixmanifest") {
     subType = "Designer";
   }
-  if (const char* c = sf->GetProperty("VS_COPY_TO_OUT_DIR")) {
+  if (cmProp c = sf->GetProperty("VS_COPY_TO_OUT_DIR")) {
     tool = "Content";
-    copyToOutDir = c;
+    copyToOutDir = *c;
     toolHasSettings = true;
   }
   if (sf->GetPropertyAsBool("VS_INCLUDE_IN_VSIX")) {
@@ -1936,23 +1936,23 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
     }
   }
 
-  const char* toolOverride = sf->GetProperty("VS_TOOL_OVERRIDE");
-  if (toolOverride && *toolOverride) {
-    tool = toolOverride;
+  cmProp toolOverride = sf->GetProperty("VS_TOOL_OVERRIDE");
+  if (toolOverride && !toolOverride->empty()) {
+    tool = toolOverride->c_str();
   }
 
   std::string deployContent;
   std::string deployLocation;
   if (this->GlobalGenerator->TargetsWindowsPhone() ||
       this->GlobalGenerator->TargetsWindowsStore()) {
-    const char* content = sf->GetProperty("VS_DEPLOYMENT_CONTENT");
-    if (content && *content) {
+    cmProp content = sf->GetProperty("VS_DEPLOYMENT_CONTENT");
+    if (content && !content->empty()) {
       toolHasSettings = true;
-      deployContent = content;
+      deployContent = *content;
 
-      const char* location = sf->GetProperty("VS_DEPLOYMENT_LOCATION");
-      if (location && *location) {
-        deployLocation = location;
+      cmProp location = sf->GetProperty("VS_DEPLOYMENT_LOCATION");
+      if (location && !location->empty()) {
+        deployLocation = *location;
       }
     }
   }
@@ -1962,7 +1962,7 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
       "VS_SOURCE_SETTINGS_" + std::string(tool));
     ConfigToSettings toolTargetSettings;
     if (toolTargetProperty) {
-      ParseSettingsProperty(toolTargetProperty->c_str(), toolTargetSettings);
+      ParseSettingsProperty(*toolTargetProperty, toolTargetSettings);
     }
 
     ParsedToolTargetSettings[tool] = toolTargetSettings;
@@ -1974,7 +1974,9 @@ void cmVisualStudio10TargetGenerator::WriteExtraSource(Elem& e1,
     }
   }
 
-  ParseSettingsProperty(sf->GetProperty("VS_SETTINGS"), toolSettings);
+  if (cmProp p = sf->GetProperty("VS_SETTINGS")) {
+    ParseSettingsProperty(*p, toolSettings);
+  }
 
   if (!toolSettings.empty()) {
     toolHasSettings = true;
@@ -2248,7 +2250,7 @@ void cmVisualStudio10TargetGenerator::WriteAllSources(Elem& e0)
           e2.Attribute("CustomUnityFile", "true");
 
           std::string unityDir = cmSystemTools::GetFilenamePath(
-            si.Source->GetProperty("UNITY_SOURCE_FILE"));
+            *si.Source->GetProperty("UNITY_SOURCE_FILE"));
           e2.Attribute("UnityFilesDirectory", unityDir);
         } else {
           // Visual Studio versions prior to 2017 15.8 do not know about unity
@@ -2293,25 +2295,25 @@ void cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags(
   bool configDependentDefines = false;
   std::string includes;
   bool configDependentIncludes = false;
-  if (const char* cflags = sf.GetProperty("COMPILE_FLAGS")) {
+  if (cmProp cflags = sf.GetProperty("COMPILE_FLAGS")) {
     configDependentFlags =
-      cmGeneratorExpression::Find(cflags) != std::string::npos;
-    flags += cflags;
+      cmGeneratorExpression::Find(*cflags) != std::string::npos;
+    flags += *cflags;
   }
-  if (const char* coptions = sf.GetProperty("COMPILE_OPTIONS")) {
+  if (cmProp coptions = sf.GetProperty("COMPILE_OPTIONS")) {
     configDependentOptions =
-      cmGeneratorExpression::Find(coptions) != std::string::npos;
-    options += coptions;
+      cmGeneratorExpression::Find(*coptions) != std::string::npos;
+    options += *coptions;
   }
-  if (const char* cdefs = sf.GetProperty("COMPILE_DEFINITIONS")) {
+  if (cmProp cdefs = sf.GetProperty("COMPILE_DEFINITIONS")) {
     configDependentDefines =
-      cmGeneratorExpression::Find(cdefs) != std::string::npos;
-    defines += cdefs;
+      cmGeneratorExpression::Find(*cdefs) != std::string::npos;
+    defines += *cdefs;
   }
-  if (const char* cincludes = sf.GetProperty("INCLUDE_DIRECTORIES")) {
+  if (cmProp cincludes = sf.GetProperty("INCLUDE_DIRECTORIES")) {
     configDependentIncludes =
-      cmGeneratorExpression::Find(cincludes) != std::string::npos;
-    includes += cincludes;
+      cmGeneratorExpression::Find(*cincludes) != std::string::npos;
+    includes += *cincludes;
   }
   std::string lang =
     this->GlobalGenerator->GetLanguageFromExtension(sf.GetExtension().c_str());
@@ -2350,13 +2352,13 @@ void cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags(
     std::string configUpper = cmSystemTools::UpperCase(config);
     std::string configDefines = defines;
     std::string defPropName = cmStrCat("COMPILE_DEFINITIONS_", configUpper);
-    if (const char* ccdefs = sf.GetProperty(defPropName)) {
+    if (cmProp ccdefs = sf.GetProperty(defPropName)) {
       if (!configDefines.empty()) {
         configDefines += ";";
       }
       configDependentDefines |=
-        cmGeneratorExpression::Find(ccdefs) != std::string::npos;
-      configDefines += ccdefs;
+        cmGeneratorExpression::Find(*ccdefs) != std::string::npos;
+      configDefines += *ccdefs;
     }
 
     // Add precompile headers compile options.
@@ -4887,8 +4889,8 @@ std::string cmVisualStudio10TargetGenerator::GetCSharpSourceLink(
     link = fullFileName.substr(srcDir.length() + 1);
   } else if (cmHasPrefix(fullFileName, binDir)) {
     link = fullFileName.substr(binDir.length() + 1);
-  } else if (const char* l = source->GetProperty("VS_CSHARP_Link")) {
-    link = l;
+  } else if (cmProp l = source->GetProperty("VS_CSHARP_Link")) {
+    link = *l;
   }
 
   ConvertToWindowsSlash(link);
diff --git a/Source/cmVisualStudio10TargetGenerator.h b/Source/cmVisualStudio10TargetGenerator.h
index e588de8..fcb72b2 100644
--- a/Source/cmVisualStudio10TargetGenerator.h
+++ b/Source/cmVisualStudio10TargetGenerator.h
@@ -242,7 +242,7 @@ private:
   std::unordered_map<std::string, ConfigToSettings> ParsedToolTargetSettings;
   bool PropertyIsSameInAllConfigs(const ConfigToSettings& toolSettings,
                                   const std::string& propName);
-  void ParseSettingsProperty(const char* settingsPropertyValue,
+  void ParseSettingsProperty(const std::string& settingsPropertyValue,
                              ConfigToSettings& toolSettings);
   std::string GetCMakeFilePath(const char* name) const;
 };
-- 
cgit v0.12