1 /*=========================================================================
3 Program: CMake - Cross-Platform Makefile Generator
4 Module: $RCSfile: cmDocumentation.cxx,v $
6 Date: $Date: 2008-03-05 16:05:20 $
7 Version: $Revision: 1.69 $
9 Copyright (c) 2002 Kitware, Inc., Insight Consortium. All rights reserved.
10 See Copyright.txt or http://www.cmake.org/HTML/Copyright.html for details.
12 This software is distributed WITHOUT ANY WARRANTY; without even
13 the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
14 PURPOSE. See the above copyright notices for more information.
16 =========================================================================*/
17 #include "cmDocumentation.h"
19 #include "cmSystemTools.h"
20 #include "cmVersion.h"
21 #include <cmsys/Directory.hxx>
24 //----------------------------------------------------------------------------
25 static const char *cmDocumentationStandardOptions
[][3] =
27 {"--copyright [file]", "Print the CMake copyright and exit.",
28 "If a file is specified, the copyright is written into it."},
29 {"--help", "Print usage information and exit.",
30 "Usage describes the basic command line interface and its options."},
31 {"--help-full [file]", "Print full help and exit.",
32 "Full help displays most of the documentation provided by the UNIX "
33 "man page. It is provided for use on non-UNIX platforms, but is "
34 "also convenient if the man page is not installed. If a file is "
35 "specified, the help is written into it."},
36 {"--help-html [file]", "Print full help in HTML format.",
37 "This option is used by CMake authors to help produce web pages. "
38 "If a file is specified, the help is written into it."},
39 {"--help-man [file]", "Print full help as a UNIX man page and exit.",
40 "This option is used by the cmake build to generate the UNIX man page. "
41 "If a file is specified, the help is written into it."},
42 {"--version [file]", "Show program name/version banner and exit.",
43 "If a file is specified, the version is written into it."},
47 //----------------------------------------------------------------------------
48 static const char *cmModulesDocumentationDescription
[][3] =
51 " CMake Modules - Modules coming with CMake, the Cross-Platform Makefile "
53 // CMAKE_DOCUMENTATION_OVERVIEW,
55 "This is the documentation for the modules and scripts coming with CMake. "
56 "Using these modules you can check the computer system for "
57 "installed software packages, features of the compiler and the "
58 "existance of headers to name just a few.", 0},
62 //----------------------------------------------------------------------------
63 static const char *cmCustomModulesDocumentationDescription
[][3] =
66 " Custom CMake Modules - Additional Modules for CMake.", 0},
67 // CMAKE_DOCUMENTATION_OVERVIEW,
69 "This is the documentation for additional modules and scripts for CMake. "
70 "Using these modules you can check the computer system for "
71 "installed software packages, features of the compiler and the "
72 "existance of headers to name just a few.", 0},
76 //----------------------------------------------------------------------------
77 static const char *cmPropertiesDocumentationDescription
[][3] =
80 " CMake Properties - Properties supported by CMake, "
81 "the Cross-Platform Makefile Generator.", 0},
82 // CMAKE_DOCUMENTATION_OVERVIEW,
84 "This is the documentation for the properties supported by CMake. "
85 "Properties can have different scopes. They can either be assigned to a "
86 "source file, a directory, a target or globally to CMake. By modifying the "
87 "values of properties the behaviour of the build system can be customized.",
92 //----------------------------------------------------------------------------
93 static const char *cmCompatCommandsDocumentationDescription
[][3] =
96 " CMake Compatibility Listfile Commands - "
97 "Obsolete commands supported by CMake for compatibility.", 0},
98 // CMAKE_DOCUMENTATION_OVERVIEW,
100 "This is the documentation for now obsolete listfile commands from previous "
101 "CMake versions, which are still supported for compatibility reasons. You "
102 "should instead use the newer, faster and shinier new commands. ;-)", 0},
106 //----------------------------------------------------------------------------
107 static const char *cmDocumentationModulesHeader
[][3] =
110 "The following modules are provided with CMake. "
111 "They can be used with INCLUDE(ModuleName).", 0},
115 //----------------------------------------------------------------------------
116 static const char *cmDocumentationCustomModulesHeader
[][3] =
119 "The following modules are also available for CMake. "
120 "They can be used with INCLUDE(ModuleName).", 0},
124 //----------------------------------------------------------------------------
125 static const char *cmDocumentationGeneratorsHeader
[][3] =
128 "The following generators are available on this platform:", 0},
132 //----------------------------------------------------------------------------
133 static const char *cmDocumentationStandardSeeAlso
[][3] =
136 "The following resources are available to get help using CMake:", 0},
138 "http://www.cmake.org",
139 "The primary starting point for learning about CMake."},
140 {"Frequently Asked Questions",
141 "http://www.cmake.org/Wiki/CMake_FAQ",
142 "A Wiki is provided containing answers to frequently asked questions. "},
143 {"Online Documentation",
144 "http://www.cmake.org/HTML/Documentation.html",
145 "Links to available documentation may be found on this web page."},
147 "http://www.cmake.org/HTML/MailingLists.html",
148 "For help and discussion about using cmake, a mailing list is provided at "
150 "The list is member-post-only but one may sign up on the CMake web page. "
151 "Please first read the full documentation at "
152 "http://www.cmake.org before posting questions to the list."},
154 "Summary of helpful links:\n"
155 " Home: http://www.cmake.org\n"
156 " Docs: http://www.cmake.org/HTML/Documentation.html\n"
157 " Mail: http://www.cmake.org/HTML/MailingLists.html\n"
158 " FAQ: http://www.cmake.org/Wiki/CMake_FAQ\n"
163 //----------------------------------------------------------------------------
164 static const char *cmDocumentationCopyright
[][3] =
167 "Copyright (c) 2002 Kitware, Inc., Insight Consortium. "
168 "All rights reserved.", 0},
170 "Redistribution and use in source and binary forms, with or without "
171 "modification, are permitted provided that the following conditions are "
174 "Redistributions of source code must retain the above copyright notice, "
175 "this list of conditions and the following disclaimer.", 0},
177 "Redistributions in binary form must reproduce the above copyright "
178 "notice, this list of conditions and the following disclaimer in the "
179 "documentation and/or other materials provided with the distribution.",
182 "The names of Kitware, Inc., the Insight Consortium, or the names of "
183 "any consortium members, or of any contributors, may not be used to "
184 "endorse or promote products derived from this software without "
185 "specific prior written permission.", 0},
187 "Modified source versions must be plainly marked as such, and must "
188 "not be misrepresented as being the original software.", 0},
190 "THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER AND CONTRIBUTORS "
191 "``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT "
192 "LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR "
193 "A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR "
194 "CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, "
195 "EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, "
196 "PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR "
197 "PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF "
198 "LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING "
199 "NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS "
200 "SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.", 0},
204 //----------------------------------------------------------------------------
205 cmDocumentation::cmDocumentation()
208 this->SetForm(TextForm
);
210 cmDocumentationSection
*sec
;
212 sec
= new cmDocumentationSection("Author","AUTHOR");
213 sec
->Append(cmDocumentationEntry
215 "This manual page was generated by the \"--help-man\" option.",
217 this->AllSections
["Author"] = sec
;
219 sec
= new cmDocumentationSection("Copyright","COPYRIGHT");
220 sec
->Append(cmDocumentationCopyright
);
221 this->AllSections
["Copyright"] = sec
;
223 sec
= new cmDocumentationSection("See Also","SEE ALSO");
224 sec
->Append(cmDocumentationStandardSeeAlso
);
225 this->AllSections
["Standard See Also"] = sec
;
227 sec
= new cmDocumentationSection("Options","OPTIONS");
228 sec
->Append(cmDocumentationStandardOptions
);
229 this->AllSections
["Options"] = sec
;
231 sec
= new cmDocumentationSection("Properties","PROPERTIES");
232 sec
->Append(cmPropertiesDocumentationDescription
);
233 this->AllSections
["Properties Description"] = sec
;
235 sec
= new cmDocumentationSection("Generators","GENERATORS");
236 sec
->Append(cmDocumentationGeneratorsHeader
);
237 this->AllSections
["Generators"] = sec
;
239 sec
= new cmDocumentationSection("Compatibility Commands",
240 "COMPATIBILITY COMMANDS");
241 sec
->Append(cmCompatCommandsDocumentationDescription
);
242 this->AllSections
["Compatibility Commands"] = sec
;
245 this->PropertySections
.push_back("Properties of Global Scope");
246 this->PropertySections
.push_back("Properties on Directories");
247 this->PropertySections
.push_back("Properties on Targets");
248 this->PropertySections
.push_back("Properties on Tests");
249 this->PropertySections
.push_back("Properties on Source Files");
251 this->VariableSections
.push_back("Variables that Provide Information");
252 this->VariableSections
.push_back("Variables That Change Behavior");
253 this->VariableSections
.push_back("Variables That Describe the System");
254 this->VariableSections
.push_back("Variables that Control the Build");
255 this->VariableSections
.push_back("Variables for Languages");
258 //----------------------------------------------------------------------------
259 cmDocumentation::~cmDocumentation()
261 for(std::vector
< char* >::iterator i
= this->ModuleStrings
.begin();
262 i
!= this->ModuleStrings
.end(); ++i
)
266 for(std::map
<std::string
,cmDocumentationSection
*>::iterator i
=
267 this->AllSections
.begin();
268 i
!= this->AllSections
.end(); ++i
)
274 //----------------------------------------------------------------------------
275 bool cmDocumentation::PrintCopyright(std::ostream
& os
)
277 cmDocumentationSection
*sec
= this->AllSections
["Copyright"];
278 const std::vector
<cmDocumentationEntry
> &entries
= sec
->GetEntries();
279 for(std::vector
<cmDocumentationEntry
>::const_iterator op
= entries
.begin();
280 op
!= entries
.end(); ++op
)
285 this->TextFormatter
.SetIndent(" ");
286 this->TextFormatter
.PrintColumn(os
, op
->Brief
.c_str());
290 this->TextFormatter
.SetIndent("");
291 this->TextFormatter
.PrintColumn(os
, op
->Brief
.c_str());
298 //----------------------------------------------------------------------------
299 bool cmDocumentation::PrintVersion(std::ostream
& os
)
301 os
<< this->GetNameString() << " version "
302 << cmVersion::GetCMakeVersion() << "\n";
306 //----------------------------------------------------------------------------
307 void cmDocumentation::AddSectionToPrint(const char *section
)
309 if (this->AllSections
.find(section
) != this->AllSections
.end())
311 this->PrintSections
.push_back(this->AllSections
[section
]);
315 //----------------------------------------------------------------------------
316 void cmDocumentation::ClearSections()
318 this->PrintSections
.erase(this->PrintSections
.begin(),
319 this->PrintSections
.end());
320 this->ModulesFound
.clear();
323 //----------------------------------------------------------------------------
324 bool cmDocumentation::PrintDocumentation(Type ht
, std::ostream
& os
)
326 if ((this->CurrentFormatter
->GetForm() != HTMLForm
)
327 && (this->CurrentFormatter
->GetForm() != DocbookForm
)
328 && (this->CurrentFormatter
->GetForm() != ManForm
))
330 this->PrintVersion(os
);
335 case cmDocumentation::Usage
:
336 return this->PrintDocumentationUsage(os
);
337 case cmDocumentation::Single
:
338 return this->PrintDocumentationSingle(os
);
339 case cmDocumentation::SingleModule
:
340 return this->PrintDocumentationSingleModule(os
);
341 case cmDocumentation::SinglePolicy
:
342 return this->PrintDocumentationSinglePolicy(os
);
343 case cmDocumentation::SingleProperty
:
344 return this->PrintDocumentationSingleProperty(os
);
345 case cmDocumentation::SingleVariable
:
346 return this->PrintDocumentationSingleVariable(os
);
347 case cmDocumentation::List
:
348 this->PrintDocumentationList(os
,"Commands");
349 this->PrintDocumentationList(os
,"Compatibility Commands");
351 case cmDocumentation::ModuleList
:
352 // find the modules first, print the custom module docs only if
353 // any custom modules have been found actually, Alex
354 this->CreateCustomModulesSection();
355 this->CreateModulesSection();
356 if (this->AllSections
.find("Custom CMake Modules")
357 != this->AllSections
.end())
359 this->PrintDocumentationList(os
,"Custom CMake Modules");
361 this->PrintDocumentationList(os
,"Modules");
363 case cmDocumentation::PropertyList
:
364 this->PrintDocumentationList(os
,"Properties Description");
365 for (std::vector
<std::string
>::iterator i
=
366 this->PropertySections
.begin();
367 i
!= this->PropertySections
.end(); ++i
)
369 this->PrintDocumentationList(os
,i
->c_str());
372 case cmDocumentation::VariableList
:
373 for (std::vector
<std::string
>::iterator i
=
374 this->VariableSections
.begin();
375 i
!= this->VariableSections
.end(); ++i
)
377 this->PrintDocumentationList(os
,i
->c_str());
380 case cmDocumentation::Full
:
381 return this->PrintDocumentationFull(os
);
382 case cmDocumentation::Modules
:
383 return this->PrintDocumentationModules(os
);
384 case cmDocumentation::CustomModules
:
385 return this->PrintDocumentationCustomModules(os
);
386 case cmDocumentation::Policies
:
387 return this->PrintDocumentationPolicies(os
);
388 case cmDocumentation::Properties
:
389 return this->PrintDocumentationProperties(os
);
390 case cmDocumentation::Variables
:
391 return this->PrintDocumentationVariables(os
);
392 case cmDocumentation::Commands
:
393 return this->PrintDocumentationCurrentCommands(os
);
394 case cmDocumentation::CompatCommands
:
395 return this->PrintDocumentationCompatCommands(os
);
397 case cmDocumentation::Copyright
:
398 return this->PrintCopyright(os
);
399 case cmDocumentation::Version
:
401 default: return false;
405 //----------------------------------------------------------------------------
406 bool cmDocumentation::CreateModulesSection()
408 cmDocumentationSection
*sec
=
409 new cmDocumentationSection("Standard CMake Modules", "MODULES");
410 this->AllSections
["Modules"] = sec
;
411 std::string cmakeModules
= this->CMakeRoot
;
412 cmakeModules
+= "/Modules";
413 cmsys::Directory dir
;
414 dir
.Load(cmakeModules
.c_str());
415 if (dir
.GetNumberOfFiles() > 0)
417 sec
->Append(cmDocumentationModulesHeader
[0]);
418 sec
->Append(cmModulesDocumentationDescription
);
419 this->CreateModuleDocsForDir(dir
, *this->AllSections
["Modules"]);
424 //----------------------------------------------------------------------------
425 bool cmDocumentation::CreateCustomModulesSection()
427 bool sectionHasHeader
= false;
429 std::vector
<std::string
> dirs
;
430 cmSystemTools::ExpandListArgument(this->CMakeModulePath
, dirs
);
432 for(std::vector
<std::string
>::const_iterator dirIt
= dirs
.begin();
436 cmsys::Directory dir
;
437 dir
.Load(dirIt
->c_str());
438 if (dir
.GetNumberOfFiles() > 0)
440 if (!sectionHasHeader
)
442 cmDocumentationSection
*sec
=
443 new cmDocumentationSection("Custom CMake Modules","CUSTOM MODULES");
444 this->AllSections
["Custom CMake Modules"] = sec
;
445 sec
->Append(cmDocumentationCustomModulesHeader
[0]);
446 sec
->Append(cmCustomModulesDocumentationDescription
);
447 sectionHasHeader
= true;
449 this->CreateModuleDocsForDir
450 (dir
, *this->AllSections
["Custom CMake Modules"]);
457 //----------------------------------------------------------------------------
459 ::CreateModuleDocsForDir(cmsys::Directory
& dir
,
460 cmDocumentationSection
&moduleSection
)
462 // sort the files alphabetically, so the docs for one module are easier
463 // to find than if they are in random order
464 std::vector
<std::string
> sortedFiles
;
465 for(unsigned int i
= 0; i
< dir
.GetNumberOfFiles(); ++i
)
467 sortedFiles
.push_back(dir
.GetFile(i
));
469 std::sort(sortedFiles
.begin(), sortedFiles
.end());
471 for(std::vector
<std::string
>::const_iterator fname
= sortedFiles
.begin();
472 fname
!=sortedFiles
.end(); ++fname
)
474 if(fname
->length() > 6)
476 if(fname
->substr(fname
->length()-6, 6) == ".cmake")
478 std::string moduleName
= fname
->substr(0, fname
->length()-6);
479 // this check is to avoid creating documentation for the modules with
480 // the same name in multiple directories of CMAKE_MODULE_PATH
481 if (this->ModulesFound
.find(moduleName
) == this->ModulesFound
.end())
483 this->ModulesFound
.insert(moduleName
);
484 std::string path
= dir
.GetPath();
487 this->CreateSingleModule(path
.c_str(), moduleName
.c_str(),
495 //----------------------------------------------------------------------------
496 bool cmDocumentation::CreateSingleModule(const char* fname
,
497 const char* moduleName
,
498 cmDocumentationSection
&moduleSection
)
500 std::ifstream
fin(fname
);
503 std::cerr
<< "Internal error: can not open module." << fname
<< std::endl
;
510 bool newParagraph
= true;
511 while ( fin
&& cmSystemTools::GetLineFromStream(fin
, line
) )
513 if(line
.size() && line
[0] == '#')
521 else if(line
[2] == '-')
523 brief
= line
.c_str()+4;
528 if(line
[1] == ' ' && line
[2] == ' ')
535 // Skip #, and leave space for preformatted
536 text
+= line
.c_str()+1;
539 else if(line
[1] == ' ')
545 newParagraph
= false;
547 text
+= line
.c_str()+2;
555 newParagraph
= false;
557 text
+= line
.c_str()+1;
563 if(text
.length() < 2 && brief
.length() == 1)
567 char* pname
= strcpy(new char[strlen(moduleName
)+1], moduleName
);
568 char* ptext
= strcpy(new char[text
.length()+1], text
.c_str());
569 this->ModuleStrings
.push_back(pname
);
570 this->ModuleStrings
.push_back(ptext
);
571 char* pbrief
= strcpy(new char[brief
.length()+1], brief
.c_str());
572 this->ModuleStrings
.push_back(pbrief
);
573 moduleSection
.Append(pname
, pbrief
, ptext
);
581 //----------------------------------------------------------------------------
582 bool cmDocumentation::PrintRequestedDocumentation(std::ostream
& os
)
586 // Loop over requested documentation types.
587 for(std::vector
<RequestedHelpItem
>::const_iterator
588 i
= this->RequestedHelpItems
.begin();
589 i
!= this->RequestedHelpItems
.end();
592 this->SetForm(i
->HelpForm
);
593 this->CurrentArgument
= i
->Argument
;
594 // If a file name was given, use it. Otherwise, default to the
596 std::ofstream
* fout
= 0;
597 std::ostream
* s
= &os
;
598 if(i
->Filename
.length() > 0)
600 fout
= new std::ofstream(i
->Filename
.c_str(), std::ios::out
);
611 // Print this documentation type to the stream.
612 if(!this->PrintDocumentation(i
->HelpType
, *s
) || !*s
)
617 // Close the file if we wrote one.
626 #define GET_OPT_ARGUMENT(target) \
627 if((i+1 < argc) && !this->IsOption(argv[i+1])) \
629 target = argv[i+1]; \
634 cmDocumentation::Form
cmDocumentation::GetFormFromFilename(
635 const std::string
& filename
)
637 std::string ext
= cmSystemTools::GetFilenameExtension(filename
);
638 ext
= cmSystemTools::UpperCase(ext
);
639 if ((ext
== ".HTM") || (ext
== ".HTML"))
641 return cmDocumentation::HTMLForm
;
644 if (ext
== ".DOCBOOK")
646 return cmDocumentation::DocbookForm
;
649 // ".1" to ".9" should be manpages
650 if ((ext
.length()==2) && (ext
[1] >='1') && (ext
[1]<='9'))
652 return cmDocumentation::ManForm
;
655 return cmDocumentation::TextForm
;
658 //----------------------------------------------------------------------------
659 bool cmDocumentation::CheckOptions(int argc
, const char* const* argv
)
661 // Providing zero arguments gives usage information.
664 RequestedHelpItem help
;
665 help
.HelpType
= cmDocumentation::Usage
;
666 help
.HelpForm
= cmDocumentation::UsageForm
;
667 this->RequestedHelpItems
.push_back(help
);
671 // Search for supported help options.
674 for(int i
=1; i
< argc
; ++i
)
676 RequestedHelpItem help
;
677 // Check if this is a supported help option.
678 if((strcmp(argv
[i
], "-help") == 0) ||
679 (strcmp(argv
[i
], "--help") == 0) ||
680 (strcmp(argv
[i
], "/?") == 0) ||
681 (strcmp(argv
[i
], "-usage") == 0) ||
682 (strcmp(argv
[i
], "-h") == 0) ||
683 (strcmp(argv
[i
], "-H") == 0))
685 help
.HelpType
= cmDocumentation::Usage
;
686 help
.HelpForm
= cmDocumentation::UsageForm
;
687 GET_OPT_ARGUMENT(help
.Argument
);
688 help
.Argument
= cmSystemTools::LowerCase(help
.Argument
);
689 // special case for single command
690 if (!help
.Argument
.empty())
692 help
.HelpType
= cmDocumentation::Single
;
695 else if(strcmp(argv
[i
], "--help-properties") == 0)
697 help
.HelpType
= cmDocumentation::Properties
;
698 GET_OPT_ARGUMENT(help
.Filename
);
699 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
701 else if(strcmp(argv
[i
], "--help-policies") == 0)
703 help
.HelpType
= cmDocumentation::Policies
;
704 GET_OPT_ARGUMENT(help
.Filename
);
705 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
707 else if(strcmp(argv
[i
], "--help-variables") == 0)
709 help
.HelpType
= cmDocumentation::Variables
;
710 GET_OPT_ARGUMENT(help
.Filename
);
711 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
713 else if(strcmp(argv
[i
], "--help-modules") == 0)
715 help
.HelpType
= cmDocumentation::Modules
;
716 GET_OPT_ARGUMENT(help
.Filename
);
717 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
719 else if(strcmp(argv
[i
], "--help-custom-modules") == 0)
721 help
.HelpType
= cmDocumentation::CustomModules
;
722 GET_OPT_ARGUMENT(help
.Filename
);
723 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
725 else if(strcmp(argv
[i
], "--help-commands") == 0)
727 help
.HelpType
= cmDocumentation::Commands
;
728 GET_OPT_ARGUMENT(help
.Filename
);
729 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
731 else if(strcmp(argv
[i
], "--help-compatcommands") == 0)
733 help
.HelpType
= cmDocumentation::CompatCommands
;
734 GET_OPT_ARGUMENT(help
.Filename
);
735 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
737 else if(strcmp(argv
[i
], "--help-full") == 0)
739 help
.HelpType
= cmDocumentation::Full
;
740 GET_OPT_ARGUMENT(help
.Filename
);
741 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
743 else if(strcmp(argv
[i
], "--help-html") == 0)
745 help
.HelpType
= cmDocumentation::Full
;
746 GET_OPT_ARGUMENT(help
.Filename
);
747 help
.HelpForm
= cmDocumentation::HTMLForm
;
749 else if(strcmp(argv
[i
], "--help-man") == 0)
751 help
.HelpType
= cmDocumentation::Full
;
752 GET_OPT_ARGUMENT(help
.Filename
);
753 help
.HelpForm
= cmDocumentation::ManForm
;
755 else if(strcmp(argv
[i
], "--help-command") == 0)
757 help
.HelpType
= cmDocumentation::Single
;
758 GET_OPT_ARGUMENT(help
.Argument
);
759 GET_OPT_ARGUMENT(help
.Filename
);
760 help
.Argument
= cmSystemTools::LowerCase(help
.Argument
);
761 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
763 else if(strcmp(argv
[i
], "--help-module") == 0)
765 help
.HelpType
= cmDocumentation::SingleModule
;
766 GET_OPT_ARGUMENT(help
.Argument
);
767 GET_OPT_ARGUMENT(help
.Filename
);
768 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
770 else if(strcmp(argv
[i
], "--help-property") == 0)
772 help
.HelpType
= cmDocumentation::SingleProperty
;
773 GET_OPT_ARGUMENT(help
.Argument
);
774 GET_OPT_ARGUMENT(help
.Filename
);
775 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
777 else if(strcmp(argv
[i
], "--help-policy") == 0)
779 help
.HelpType
= cmDocumentation::SinglePolicy
;
780 GET_OPT_ARGUMENT(help
.Argument
);
781 GET_OPT_ARGUMENT(help
.Filename
);
782 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
784 else if(strcmp(argv
[i
], "--help-variable") == 0)
786 help
.HelpType
= cmDocumentation::SingleVariable
;
787 GET_OPT_ARGUMENT(help
.Argument
);
788 GET_OPT_ARGUMENT(help
.Filename
);
789 help
.HelpForm
= this->GetFormFromFilename(help
.Filename
);
791 else if(strcmp(argv
[i
], "--help-command-list") == 0)
793 help
.HelpType
= cmDocumentation::List
;
794 GET_OPT_ARGUMENT(help
.Filename
);
795 help
.HelpForm
= cmDocumentation::TextForm
;
797 else if(strcmp(argv
[i
], "--help-module-list") == 0)
799 help
.HelpType
= cmDocumentation::ModuleList
;
800 GET_OPT_ARGUMENT(help
.Filename
);
801 help
.HelpForm
= cmDocumentation::TextForm
;
803 else if(strcmp(argv
[i
], "--help-property-list") == 0)
805 help
.HelpType
= cmDocumentation::PropertyList
;
806 GET_OPT_ARGUMENT(help
.Filename
);
807 help
.HelpForm
= cmDocumentation::TextForm
;
809 else if(strcmp(argv
[i
], "--help-variable-list") == 0)
811 help
.HelpType
= cmDocumentation::VariableList
;
812 GET_OPT_ARGUMENT(help
.Filename
);
813 help
.HelpForm
= cmDocumentation::TextForm
;
815 else if(strcmp(argv
[i
], "--copyright") == 0)
817 help
.HelpType
= cmDocumentation::Copyright
;
818 GET_OPT_ARGUMENT(help
.Filename
);
819 help
.HelpForm
= cmDocumentation::UsageForm
;
821 else if((strcmp(argv
[i
], "--version") == 0) ||
822 (strcmp(argv
[i
], "-version") == 0) ||
823 (strcmp(argv
[i
], "/V") == 0))
825 help
.HelpType
= cmDocumentation::Version
;
826 GET_OPT_ARGUMENT(help
.Filename
);
827 help
.HelpForm
= cmDocumentation::UsageForm
;
829 if(help
.HelpType
!= None
)
831 // This is a help option. See if there is a file name given.
833 this->RequestedHelpItems
.push_back(help
);
839 //----------------------------------------------------------------------------
840 void cmDocumentation::Print(Form f
, std::ostream
& os
)
846 //----------------------------------------------------------------------------
847 void cmDocumentation::Print(std::ostream
& os
)
849 // if the formatter supports it, print a master index for
851 this->CurrentFormatter
->PrintIndex(os
, this->PrintSections
);
852 for(unsigned int i
=0; i
< this->PrintSections
.size(); ++i
)
854 std::string name
= this->PrintSections
[i
]->
855 GetName((this->CurrentFormatter
->GetForm()));
856 this->CurrentFormatter
->PrintSection(os
,*this->PrintSections
[i
],
861 //----------------------------------------------------------------------------
862 void cmDocumentation::SetName(const char* name
)
864 this->NameString
= name
?name
:"";
867 //----------------------------------------------------------------------------
868 void cmDocumentation::SetSection(const char *name
,
869 cmDocumentationSection
*section
)
871 if (this->AllSections
.find(name
) != this->AllSections
.end())
873 delete this->AllSections
[name
];
875 this->AllSections
[name
] = section
;
878 //----------------------------------------------------------------------------
879 void cmDocumentation::SetSection(const char *name
,
880 std::vector
<cmDocumentationEntry
> &docs
)
882 cmDocumentationSection
*sec
=
883 new cmDocumentationSection(name
,
884 cmSystemTools::UpperCase(name
).c_str());
886 this->SetSection(name
,sec
);
889 //----------------------------------------------------------------------------
890 void cmDocumentation::SetSection(const char *name
,
891 const char *docs
[][3])
893 cmDocumentationSection
*sec
=
894 new cmDocumentationSection(name
,
895 cmSystemTools::UpperCase(name
).c_str());
897 this->SetSection(name
,sec
);
900 //----------------------------------------------------------------------------
902 ::SetSections(std::map
<std::string
,cmDocumentationSection
*> §ions
)
904 for (std::map
<std::string
,cmDocumentationSection
*>::const_iterator
905 it
= sections
.begin(); it
!= sections
.end(); ++it
)
907 this->SetSection(it
->first
.c_str(),it
->second
);
911 //----------------------------------------------------------------------------
912 void cmDocumentation::PrependSection(const char *name
,
913 const char *docs
[][3])
915 cmDocumentationSection
*sec
= 0;
916 if (this->AllSections
.find(name
) == this->AllSections
.end())
918 sec
= new cmDocumentationSection
919 (name
, cmSystemTools::UpperCase(name
).c_str());
920 this->SetSection(name
,sec
);
924 sec
= this->AllSections
[name
];
929 //----------------------------------------------------------------------------
930 void cmDocumentation::PrependSection(const char *name
,
931 std::vector
<cmDocumentationEntry
> &docs
)
933 cmDocumentationSection
*sec
= 0;
934 if (this->AllSections
.find(name
) == this->AllSections
.end())
936 sec
= new cmDocumentationSection
937 (name
, cmSystemTools::UpperCase(name
).c_str());
938 this->SetSection(name
,sec
);
942 sec
= this->AllSections
[name
];
947 //----------------------------------------------------------------------------
948 void cmDocumentation::AppendSection(const char *name
,
949 const char *docs
[][3])
951 cmDocumentationSection
*sec
= 0;
952 if (this->AllSections
.find(name
) == this->AllSections
.end())
954 sec
= new cmDocumentationSection
955 (name
, cmSystemTools::UpperCase(name
).c_str());
956 this->SetSection(name
,sec
);
960 sec
= this->AllSections
[name
];
965 //----------------------------------------------------------------------------
966 void cmDocumentation::AppendSection(const char *name
,
967 std::vector
<cmDocumentationEntry
> &docs
)
969 cmDocumentationSection
*sec
= 0;
970 if (this->AllSections
.find(name
) == this->AllSections
.end())
972 sec
= new cmDocumentationSection
973 (name
, cmSystemTools::UpperCase(name
).c_str());
974 this->SetSection(name
,sec
);
978 sec
= this->AllSections
[name
];
983 //----------------------------------------------------------------------------
984 void cmDocumentation::AppendSection(const char *name
,
985 cmDocumentationEntry
&docs
)
988 std::vector
<cmDocumentationEntry
> docsVec
;
989 docsVec
.push_back(docs
);
990 this->AppendSection(name
,docsVec
);
993 //----------------------------------------------------------------------------
994 void cmDocumentation::PrependSection(const char *name
,
995 cmDocumentationEntry
&docs
)
998 std::vector
<cmDocumentationEntry
> docsVec
;
999 docsVec
.push_back(docs
);
1000 this->PrependSection(name
,docsVec
);
1003 //----------------------------------------------------------------------------
1004 void cmDocumentation::SetSeeAlsoList(const char *data
[][3])
1006 cmDocumentationSection
*sec
=
1007 new cmDocumentationSection("See Also", "SEE ALSO");
1008 this->AllSections
["See Also"] = sec
;
1009 this->SeeAlsoString
= ".B ";
1013 this->SeeAlsoString
+= data
[i
][1];
1014 this->SeeAlsoString
+= data
[i
+1][1]? "(1), ":"(1)";
1017 sec
->Append(0,this->SeeAlsoString
.c_str(),0);
1018 sec
->Append(cmDocumentationStandardSeeAlso
);
1021 //----------------------------------------------------------------------------
1022 bool cmDocumentation::PrintDocumentationGeneric(std::ostream
& os
,
1023 const char *section
)
1025 if(this->AllSections
.find(section
) == this->AllSections
.end())
1027 os
<< "Internal error: " << section
<< " list is empty." << std::endl
;
1030 if(this->CurrentArgument
.length() == 0)
1032 os
<< "Required argument missing.\n";
1035 const std::vector
<cmDocumentationEntry
> &entries
=
1036 this->AllSections
[section
]->GetEntries();
1037 for(std::vector
<cmDocumentationEntry
>::const_iterator ei
=
1039 ei
!= entries
.end(); ++ei
)
1041 if(this->CurrentArgument
== ei
->Name
)
1043 this->PrintDocumentationCommand(os
, *ei
);
1050 //----------------------------------------------------------------------------
1051 bool cmDocumentation::PrintDocumentationSingle(std::ostream
& os
)
1053 if (this->PrintDocumentationGeneric(os
,"Commands"))
1057 if (this->PrintDocumentationGeneric(os
,"Compatibility Commands"))
1062 // Argument was not a command. Complain.
1063 os
<< "Argument \"" << this->CurrentArgument
.c_str()
1064 << "\" to --help-command is not a CMake command. "
1065 << "Use --help-command-list to see all commands.\n";
1069 //----------------------------------------------------------------------------
1070 bool cmDocumentation::PrintDocumentationSingleModule(std::ostream
& os
)
1072 if(this->CurrentArgument
.length() == 0)
1074 os
<< "Argument --help-module needs a module name.\n";
1078 std::string moduleName
;
1080 std::vector
<std::string
> dirs
;
1081 cmSystemTools::ExpandListArgument(this->CMakeModulePath
, dirs
);
1082 for(std::vector
<std::string
>::const_iterator dirIt
= dirs
.begin();
1083 dirIt
!= dirs
.end();
1086 moduleName
= *dirIt
;
1088 moduleName
+= this->CurrentArgument
;
1089 moduleName
+= ".cmake";
1090 if(cmSystemTools::FileExists(moduleName
.c_str()))
1097 if (moduleName
.empty())
1099 moduleName
= this->CMakeRoot
;
1100 moduleName
+= "/Modules/";
1101 moduleName
+= this->CurrentArgument
;
1102 moduleName
+= ".cmake";
1103 if(!cmSystemTools::FileExists(moduleName
.c_str()))
1109 if(!moduleName
.empty())
1111 cmDocumentationSection
*sec
=
1112 new cmDocumentationSection("Standard CMake Modules", "MODULES");
1113 this->AllSections
["Modules"] = sec
;
1114 if (this->CreateSingleModule(moduleName
.c_str(),
1115 this->CurrentArgument
.c_str(),
1116 *this->AllSections
["Modules"]))
1118 this->PrintDocumentationCommand
1119 (os
, this->AllSections
["Modules"]->GetEntries()[0]);
1120 os
<< "\n Defined in: ";
1121 os
<< moduleName
<< "\n";
1126 // Argument was not a module. Complain.
1127 os
<< "Argument \"" << this->CurrentArgument
.c_str()
1128 << "\" to --help-module is not a CMake module.\n";
1132 //----------------------------------------------------------------------------
1133 bool cmDocumentation::PrintDocumentationSingleProperty(std::ostream
& os
)
1136 for (std::vector
<std::string
>::iterator i
=
1137 this->PropertySections
.begin();
1138 !done
&& i
!= this->PropertySections
.end(); ++i
)
1140 done
= this->PrintDocumentationGeneric(os
,i
->c_str());
1148 // Argument was not a command. Complain.
1149 os
<< "Argument \"" << this->CurrentArgument
.c_str()
1150 << "\" to --help-property is not a CMake property. "
1151 << "Use --help-property-list to see all properties.\n";
1155 //----------------------------------------------------------------------------
1156 bool cmDocumentation::PrintDocumentationSinglePolicy(std::ostream
& os
)
1158 if (this->PrintDocumentationGeneric(os
,"Policies"))
1163 // Argument was not a command. Complain.
1164 os
<< "Argument \"" << this->CurrentArgument
.c_str()
1165 << "\" to --help-policy is not a CMake policy.\n";
1169 //----------------------------------------------------------------------------
1170 bool cmDocumentation::PrintDocumentationSingleVariable(std::ostream
& os
)
1173 for (std::vector
<std::string
>::iterator i
=
1174 this->VariableSections
.begin();
1175 !done
&& i
!= this->VariableSections
.end(); ++i
)
1177 done
= this->PrintDocumentationGeneric(os
,i
->c_str());
1185 // Argument was not a command. Complain.
1186 os
<< "Argument \"" << this->CurrentArgument
.c_str()
1187 << "\" to --help-variable is not a defined variable. "
1188 << "Use --help-variable-list to see all defined variables.\n";
1192 //----------------------------------------------------------------------------
1193 bool cmDocumentation::PrintDocumentationList(std::ostream
& os
,
1194 const char *section
)
1196 if(this->AllSections
.find(section
) == this->AllSections
.end())
1198 os
<< "Internal error: " << section
<< " list is empty." << std::endl
;
1202 const std::vector
<cmDocumentationEntry
> &entries
=
1203 this->AllSections
[section
]->GetEntries();
1204 for(std::vector
<cmDocumentationEntry
>::const_iterator ei
=
1206 ei
!= entries
.end(); ++ei
)
1210 os
<< ei
->Name
<< std::endl
;
1216 //----------------------------------------------------------------------------
1217 bool cmDocumentation::PrintDocumentationUsage(std::ostream
& os
)
1219 this->ClearSections();
1220 this->AddSectionToPrint("Usage");
1221 this->AddSectionToPrint("Options");
1222 this->AddSectionToPrint("Generators");
1227 //----------------------------------------------------------------------------
1228 bool cmDocumentation::PrintDocumentationFull(std::ostream
& os
)
1230 this->CreateFullDocumentation();
1231 this->CurrentFormatter
->PrintHeader(GetNameString(), os
);
1233 this->CurrentFormatter
->PrintFooter(os
);
1237 //----------------------------------------------------------------------------
1238 bool cmDocumentation::PrintDocumentationModules(std::ostream
& os
)
1240 this->ClearSections();
1241 this->CreateModulesSection();
1242 this->AddSectionToPrint("Description");
1243 this->AddSectionToPrint("Modules");
1244 this->AddSectionToPrint("Copyright");
1245 this->AddSectionToPrint("See Also");
1246 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1248 this->CurrentFormatter
->PrintFooter(os
);
1252 //----------------------------------------------------------------------------
1253 bool cmDocumentation::PrintDocumentationCustomModules(std::ostream
& os
)
1255 this->ClearSections();
1256 this->CreateCustomModulesSection();
1257 this->AddSectionToPrint("Description");
1258 this->AddSectionToPrint("Custom CMake Modules");
1259 // the custom modules are most probably not under Kitware's copyright, Alex
1260 // this->AddSectionToPrint("Copyright");
1261 this->AddSectionToPrint("See Also");
1263 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1265 this->CurrentFormatter
->PrintFooter(os
);
1269 //----------------------------------------------------------------------------
1270 bool cmDocumentation::PrintDocumentationPolicies(std::ostream
& os
)
1272 this->ClearSections();
1273 this->AddSectionToPrint("Description");
1274 this->AddSectionToPrint("Policies");
1275 this->AddSectionToPrint("Copyright");
1276 this->AddSectionToPrint("See Also");
1278 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1280 this->CurrentFormatter
->PrintFooter(os
);
1284 //----------------------------------------------------------------------------
1285 bool cmDocumentation::PrintDocumentationProperties(std::ostream
& os
)
1287 this->ClearSections();
1288 this->AddSectionToPrint("Properties Description");
1289 for (std::vector
<std::string
>::iterator i
=
1290 this->PropertySections
.begin();
1291 i
!= this->PropertySections
.end(); ++i
)
1293 this->AddSectionToPrint(i
->c_str());
1295 this->AddSectionToPrint("Copyright");
1296 this->AddSectionToPrint("Standard See Also");
1297 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1299 this->CurrentFormatter
->PrintFooter(os
);
1303 //----------------------------------------------------------------------------
1304 bool cmDocumentation::PrintDocumentationVariables(std::ostream
& os
)
1306 this->ClearSections();
1307 for (std::vector
<std::string
>::iterator i
=
1308 this->VariableSections
.begin();
1309 i
!= this->VariableSections
.end(); ++i
)
1311 this->AddSectionToPrint(i
->c_str());
1313 this->AddSectionToPrint("Copyright");
1314 this->AddSectionToPrint("Standard See Also");
1315 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1317 this->CurrentFormatter
->PrintFooter(os
);
1321 //----------------------------------------------------------------------------
1322 bool cmDocumentation::PrintDocumentationCurrentCommands(std::ostream
& os
)
1324 this->ClearSections();
1325 this->AddSectionToPrint("Commands");
1326 this->AddSectionToPrint("Copyright");
1327 this->AddSectionToPrint("Standard See Also");
1328 this->CurrentFormatter
->PrintHeader(this->GetNameString(), os
);
1330 this->CurrentFormatter
->PrintFooter(os
);
1334 //----------------------------------------------------------------------------
1335 bool cmDocumentation::PrintDocumentationCompatCommands(std::ostream
& os
)
1337 this->ClearSections();
1338 this->AddSectionToPrint("Compatibility Commands Description");
1339 this->AddSectionToPrint("Compatibility Commands");
1340 this->AddSectionToPrint("Copyright");
1341 this->AddSectionToPrint("Standard See Also");
1342 this->CurrentFormatter
->PrintHeader(GetNameString(), os
);
1344 this->CurrentFormatter
->PrintFooter(os
);
1348 //----------------------------------------------------------------------------
1349 void cmDocumentation
1350 ::PrintDocumentationCommand(std::ostream
& os
,
1351 const cmDocumentationEntry
&entry
)
1353 cmDocumentationSection
*sec
= new cmDocumentationSection("","");
1355 this->AllSections
["temp"] = sec
;
1356 this->ClearSections();
1357 this->AddSectionToPrint("temp");
1359 this->AllSections
.erase("temp");
1363 //----------------------------------------------------------------------------
1364 void cmDocumentation::CreateFullDocumentation()
1366 this->ClearSections();
1367 this->CreateCustomModulesSection();
1368 this->CreateModulesSection();
1370 std::set
<std::string
> emitted
;
1371 this->AddSectionToPrint("Name");
1372 emitted
.insert("Name");
1373 this->AddSectionToPrint("Usage");
1374 emitted
.insert("Usage");
1375 this->AddSectionToPrint("Description");
1376 emitted
.insert("Description");
1377 this->AddSectionToPrint("Options");
1378 emitted
.insert("Options");
1379 this->AddSectionToPrint("Generators");
1380 emitted
.insert("Generators");
1381 this->AddSectionToPrint("Commands");
1382 emitted
.insert("Commands");
1385 this->AddSectionToPrint("Properties Description");
1386 emitted
.insert("Properties Description");
1387 for (std::vector
<std::string
>::iterator i
=
1388 this->PropertySections
.begin();
1389 i
!= this->PropertySections
.end(); ++i
)
1391 this->AddSectionToPrint(i
->c_str());
1392 emitted
.insert(i
->c_str());
1395 emitted
.insert("Copyright");
1396 emitted
.insert("See Also");
1397 emitted
.insert("Standard See Also");
1398 emitted
.insert("Author");
1400 // add any sections not yet written out, or to be written out
1401 for (std::map
<std::string
, cmDocumentationSection
*>::iterator i
=
1402 this->AllSections
.begin();
1403 i
!= this->AllSections
.end(); ++i
)
1405 if (emitted
.find(i
->first
) == emitted
.end())
1407 this->AddSectionToPrint(i
->first
.c_str());
1411 this->AddSectionToPrint("Copyright");
1413 if(this->CurrentFormatter
->GetForm() == ManForm
)
1415 this->AddSectionToPrint("See Also");
1416 this->AddSectionToPrint("Author");
1420 this->AddSectionToPrint("Standard See Also");
1424 //----------------------------------------------------------------------------
1425 void cmDocumentation::SetForm(Form f
)
1430 this->CurrentFormatter
= &this->HTMLFormatter
;
1433 this->CurrentFormatter
= &this->DocbookFormatter
;
1436 this->CurrentFormatter
= &this->ManFormatter
;
1439 this->CurrentFormatter
= &this->TextFormatter
;
1442 this->CurrentFormatter
= & this->UsageFormatter
;
1448 //----------------------------------------------------------------------------
1449 const char* cmDocumentation::GetNameString() const
1451 if(this->NameString
.length() > 0)
1453 return this->NameString
.c_str();
1461 //----------------------------------------------------------------------------
1462 bool cmDocumentation::IsOption(const char* arg
) const
1464 return ((arg
[0] == '-') || (strcmp(arg
, "/V") == 0) ||
1465 (strcmp(arg
, "/?") == 0));