% \iffalse meta-comment % % Copyright (c) 2019-2024 by Keith F. Prussing % % This work may be distributed and/or modified under the conditions of % the LaTeX Project Public License, either version 1.3c of this license % or (at your option) any later version. The latest version of this % license is in % % http://www.latex-project.org/lppl.txt % % and version 1.3c or later is part of all distributions of LaTeX % version 2005/12/01 or later. % % This work has the LPPL maintenance status `maintained'. % % The Current Maintainer of this work is Keith F. Prussing. % % \fi % % \iffalse %<*driver> \ProvidesFile{\jobname.dtx} % %\NeedsTeXFormat{LaTeX2e}[2003/12/01] %\ProvidesPackage{secretx} %[2024/03/07 v0.10.9 Classification marking macros] % %<*driver> \documentclass{ltxdoc} \usepackage{hypdoc} \usepackage{secretx} \fancyhead[L,C,R]{} \fancyfoot[C]{} \fancyfoot[R]{\thepage} \EnableCrossrefs \CodelineIndex \RecordChanges \usepackage{hologo} \usepackage{listings} \usepackage{mwe} \newtcolorbox{notice}{colback=red!5!white,colframe=red!75!black,% fonttitle=\bfseries,title={Notice}} \setcounter{IndexColumns}{2} \IndexPrologue{\section{Index}} \GlossaryPrologue{\section{Change History}} \usepackage[style=ieee]{biblatex} \addbibresource{secretx.bib} \usepackage{cleveref} % Command for \newcommand\barg[1]{{\ttfamily<}\meta{#1}{\ttfamily>}} \tcbuselibrary{listings} \begin{document} \DocInput{\jobname.dtx} \end{document} % % \fi % % \CheckSum{305} % % \CharacterTable % {Upper-case \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z % Lower-case \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z % Digits \0\1\2\3\4\5\6\7\8\9 % Exclamation \! Double quote \" Hash (number) \# % Dollar \$ Percent \% Ampersand \& % Acute accent \' Left paren \( Right paren \) % Asterisk \* Plus \+ Comma \, % Minus \- Point \. Solidus \/ % Colon \: Semicolon \; Less than \< % Equals \= Greater than \> Question mark \? % Commercial at \@ Left bracket \[ Backslash \\ % Right bracket \] Circumflex \^ Underscore \_ % Grave accent \` Left brace \{ Vertical bar \| % Right brace \} Tilde \~} % % \changes{v0.5}{2019/04/24}{Initial version} % \changes{v0.6}{2019/04/27}{Implementation reorganization} % \changes{v0.7}{2019/04/27}{Correctly roll over marking level} % \changes{v0.8}{2019/05/03}{Consolidate macros} % \changes{v0.8.5}{2019/05/11}{Add explicit environments} % \changes{v0.8.6}{2019/05/11}{Make all new commands robust} % \changes{v0.9.0}{2020/09/16}{Provide manual heading override} % \changes{v0.10}{2021/03/13}{Move development to trunk branch} % \GetFileInfo{\jobname.sty} % %^^A Package macros % \DoNotIndex{\begin, \end, \newenvironment, \newrobustcmd, \renewcommand} % \DoNotIndex{\csdef, \csuse, \ifcsdef, \if, \else, \fi, \everypar} % \DoNotIndex{\iftoggle, \ifnum, \toggletrue, \togglefalse, \thepage} % \DoNotIndex{\newcounter, \newtoggle, \setcounter, \stepcounter} % \DoNotIndex{\PackageError, \RequirePackage, \PackageWarning, \llap} % \DoNotIndex{\box, \setbox} % \DoNotIndex{\protect, \makebox, \parindent, \PushPostHook, \aftergroup} % \DoNotIndex{\bgroup, \egroup, \@ifclassloaded, \centering, \kern} % \DoNotIndex{\hfill, \null, \edef, \vspace, \setlist, \Large, \bfseries} % \DoNotIndex{\space, \@ifpackageloaded, \fancyfoot, \fancyhead} % \DoNotIndex{\fancypagestyle, \fbox, \ifcsempty, \ifdefstring} % \DoNotIndex{\ifnumgreater, \IfValueTF, \lastbox, \leavevmode} % \DoNotIndex{\leftmargin, \MessageBreak, \NewDocumentCommand} % \DoNotIndex{\NewTColorBox, \PushPreHook, \tcbset, \tcbtitle} % \DoNotIndex{\textwidth, \value, \usebeamerfont} %^^A Other package macros % \DoNotIndex{\AtBeginShipout} % \DoNotIndex{\lhead, \chead, \rhead, \lfoot, \cfoot, \rfoot, \fancyhf} % \DoNotIndex{\headerrulewidth, \pagestyle, \thispagestyle} % \DoNotIndex{\zref, \zref@extract, \zlabel, \defbeamertemplate} % \DoNotIndex{\BODY, \NewEnviron, \userbeamerfont, \setbeamerfont} % \DoNotIndex{\ifdefempty, \DeclareStringOption, \ProcessKeyvalOptions} % \DoNotIndex{\AtBeginEnvironment, \AtEndEnvironment} %^^A Package specific to ignore % \DoNotIndex{\thesecretx@doclevel, \thesecretx@pagelevel, \reset} % \DoNotIndex{\thesecretx@markcount, \thesecretx@currentlevel, \curcnt} %^^A Writing to the aux file macros % \DoNotIndex{\@auxout, \immediate, \\, \AtEndDocument, \write, \string} % \DoNotIndex{\space} % % \title{ % Classification Marking Macros for \LaTeX{} \thanks{This document % corresponds to \textsf{\jobname}~\fileversion, % dated~\filedate.} % } % % \author{Keith F. Prussing \\ \texttt{kprussing74@gmail.com}} % % \maketitle % \tableofcontents % \thispagestyle{secretx} % % \begin{abstract} % This package provides a set of \LaTeX{} macros for marking paragraphs % in a document with a leading string and modifying the header and the % footer of each page. This is the spiritual successor to % \textsf{secret.sty} but adds the feature of marking the header and the % footer correctly. % \end{abstract} % % \section{Introduction} % % A core component of reporting sensitive information is properly % marking sections of a document with appropriate labels. This package % aims to provide tools for helping mark a document correctly. % % \section{Usage} % \changes{v0.7.1}{2019/04/28}{Expand usage documentation} % % To install the package, simply run the provided |secretx.ins| file % through your preferred \LaTeX{} engine. Then, copy the resultant % |.sty| file to a location where \LaTeX{} can find it. To generate % the documentation, run this file (|secretx.dtx|) through \LaTeX{} % twice. The second time is only to make sure the references and index % are typeset correctly. If you have \hologo{LuaLaTeX}, you could also % run |l3build install| to install into your local texmf tree and % |l3build doc| to get a quick version of the documentation. % % \Cref{app:example} provides an example document and \textsf{beamer} % presentation showing the usage of the package. The raw source is also % provided in the \textsf{doc} directory with this reference. To see % the typeset result, simply run the example files through \LaTeX{}. % % \subsection{Marking Management} % % The basic concept behind marking each page is setting a ``level'' for % each paragraph. The highest level paragraph on any given page sets % the overall level of the page in a standard document. Before use, the % user must specify every desired marking level along with paragraph and % header markings. The header and footer markings are set with a % \textsf{fancyhdr} |\pagestyle| which is activated by default for % non-\textsf{beamer} documents. % % To apply headers and footers to \textsf{beamer} slides, use % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \usebeamertemplate{headline}[secretx] % \usebeamertemplate{footline}[secretx] % \end{lstlisting} % or simply use |\getheading| in your custom \textsf{headline} and % \textsf{footline}. Additionally, the \textsf{headline} and % \textsf{footline} themes accept an optional argument. If this matches % the string ``title'', the overall document banner is typeset instead % of the individual page banner. % % \DescribeMacro{\setmarking} % \DescribeMacro{\setheading} % To register a paragraph marking, use % |\setmarking|\marg{level}\marg{marking}. Likewise, to register a % heading use |\setheading|\marg{level}\marg{heading}. These marcos % register a \marg{marking} or \marg{heading} at the specified % \marg{level}. The user is responsible for making sure the marker and % heading for given level are consistent. Providing a level more than % once will simply overwrite the previous definition with no warning. % % \DescribeMacro{\addmarking} % |\addmarking|\marg{level}\marg{marking}\marg{heading} will set the % marking and heading at the given level. This is simply a convenience % wrapper around |\setmarking| and |\setheading|. % % \DescribeMacro{\getmarking} % \DescribeMacro{\getheading} % \changes{v0.8.4}{2019/05/11}{Use current level as default marking} % Once a level has been registered, retrieving the marking or heading is % done with |\getmarking|\oarg{level} or |\getheading|\oarg{level} % respectively. The argument defaults to the current paragraph or page % level as appropriate. These macros check that the given \oarg{level} % has a defined marking and heading. If not, these will raise an error. % These return the expanded string given to |\setmarking| and % |\setheading|. % % \DescribeMacro{\pagelevel} % \DescribeMacro{\doclevel} % These provide access to the current page and document levels. These % are read only and are provided to reveal the current state for the % user instead of having to work with the package internals. % % \DescribeMacro{\pagestyle\{secretx\}} % \changes{v0.10}{2022/03/11}{Define fancyhdr page style} % This pagestyle places the appropriate header and footer page marking % in the center of the header and footer. It changes no other parts of % the header or footer. This is loaded by default; however, it is % ultimately the users responsibility to ensure this is loaded at the % appropriate time or that other header/footer customizations do not % overwrite the center portion of either the header or footer. If you % need to have a highly customized header or footer, simply add % |\getheading| to the appropriate portion of your header or footer. % % \subsection{Document Marking} % % \DescribeMacro{\marking} % Marking a paragraph is done by specifying the numeric level with which % to mark using |\marking|\marg{level}\{\ldots\}. This macro takes care % of marking the paragraph with the appropriate marker and updating the % page and document levels. The page and document levels are only % updated if the given marking is higher than the current level. % % \DescribeEnv{marking block} % Collecting large bodies of text into a macro is not ideal. Instead, % we would like to use an environment. To this end, this package % provides the |marking block| environment. The syntax is analogous to % the |\marking| macro in that it takes a \marg{level}. For example: % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \begin{marking block}{1} % \ldots % \end{marking block} % \end{lstlisting} % % % \DescribeEnv{marking box} % \changes{v0.11}{2024/02/28}{Add marking box environment} % Graphical or tabular content can be wrapped in a |tcolorbox| to % indicate the marking level of the entire content. The |marking box| % environment will wrap the item in a colored box and place the heading % in the upper left and lower right corners of the box in the same color % as the box. The environment accepts the following options: % % \begin{enumerate} % \item \marg{level}: The level of the marking % \item \barg{top sep}: The additional separation above the content % \item \barg{bottom sep}: The additional separation below the content % \item \oarg{options}: Additional options passed to |tcolorbox| % \end{enumerate} % % Under the hood, this is a |tcolorbox| customized with the |secretx| % style. % % \iffalse %<*driver> % \fi \begin{tcblisting}{listing outside text} \setheading{1}{Marking} \begin{marking box}{1} \includegraphics% [width=\textwidth]% {example-image-a} \end{marking box} \end{tcblisting} % \iffalse % % \fi % % For convenience, we provide definitions to set common levels. The % styles and colors listed are used with |marking box| and may be % customized as described in the documentation for |tcolorbox|. These % are: % % \DescribeMacro{\unclassified} % \DescribeEnv{unclassified block} % \DescribeEnv{unclassified box} % \DescribeMacro{unclassified style} % \DescribeMacro{unclassified/color} % Mark unclassified. % \begin{itemize} % \item Level: 1 % \item Marking: \getmarking[1] % \item Heading: \getheading[1] % \end{itemize} % % \DescribeMacro{\fouo} % \DescribeEnv{fouo block} % Mark for official use only. % \begin{notice} % The FOUO marking is deprecated. This will be removed in version 0.11. % \end{notice} % \begin{itemize} % \item Level: 2 % \item Marking: \getmarking[2] % \item Heading: \getheading[2] % \end{itemize} % % \DescribeMacro{\confidential} % \DescribeEnv{confidential block} % \DescribeEnv{confidential box} % \DescribeMacro{confidential style} % \DescribeMacro{confidential/color} % Mark confidential. % \begin{itemize} % \item Level: 5 % \item Marking: \getmarking[5] % \item Heading: \getheading[5] % \end{itemize} % % \DescribeMacro{\secret} % \DescribeEnv{secret block} % \DescribeEnv{secret box} % \DescribeMacro{secret style} % \DescribeMacro{secret/color} % Mark secret. % \begin{itemize} % \item Level: 10 % \item Marking: \getmarking[10] % \item Heading: \getheading[10] % \end{itemize} % % \DescribeMacro{\secretnoforn} % \DescribeEnv{secretnoforn block} % \DescribeEnv{secretnoforn box} % \DescribeMacro{secretnoforn style} % \DescribeMacro{secretnoforn/color} % Mark secret no foreign. % \begin{itemize} % \item Level: 15 % \item Marking: \getmarking[15] % \item Heading: \getheading[15] % \end{itemize} % % \DescribeMacro{\topsecret} % \DescribeEnv{topsecret block} % \DescribeEnv{topsecret box} % \DescribeMacro{topsecret style} % \DescribeMacro{topsecret/color} % Mark top secret. % \begin{itemize} % \item Level: 25 % \item Marking: \getmarking[25] % \item Heading: \getheading[25] % \end{itemize} % % \subsection{Overriding the Default Page Marking} % % \begin{notice} % Version 0.11 will change the meaning of this option as the internal % logic is still buggy. After 0.11, |heading| will \emph{enable} the % adaptive marking. % \end{notice} % % \DescribeMacro{heading} % \changes{v0.10}{2022/03/10}{Allow default behavior of header} % Although this package attempts to automate away many of the underlying % details of marking a document, it cannot always succeed. Since it is % the final responsibility of the document author to ensure appropriate % overall markings, the |heading| argument to the package provides % a manual override to the package determined page marking per the % alternate marking advice in \cite{noauthor_marking_2021}. This % option can be given alone or assigned as a string |heading=|. % If a string is given, the text is typeset in the header and footer % verbatim. If the text is not given, the highest header marking of the % document will be used for the header and footer. The header and % footers will be the same on all pages in the document. % % If possible, we would appreciate any representative examples of usages % that fails to get marked correctly reported to the % \href{https://github.com/kprussing/secretx/issues}{issue tracker}. % However, due to the intended use of this package, we understand if % this is not practical. % % \DescribeMacro{\setlevel} % \changes{v0.10}{2021/08/17}{Add setlevel command} % This macro explicitly sets the level of a page without marking a % particular item. The focus of this is more for a class like % \textsf{beamer} where the slide may be composed solely of images % that are themselves marked but are unknown to \LaTeX{}, or floating % environment such as |figure| or |table|. This lets the user % explicitly state the classification of the proper page or scope. % % \subsection{Additional Statements} % % \DescribeMacro{\distribution} % A distribution statement is a common need for documentation. Using % |\distribution| \marg{level}\marg{reason}\marg{date of % determination}\marg{controlling DoD office} will place the appropriate % distribution statement following DoDI 5230.24\cite{dodi_5230.24}. % Here \marg{level} is the letter version of the statement (A, B, C, D, % etc.). % % \DescribeMacro{\exportcontrol} % This macro places the export control warning in a framed box at the % current location in accordance with DoDI 5230.24\cite{dodi_5230.24}. % The default is to typeset the box at 90\% of the |\textwidth|. Using % |\exportcontrol|\oarg{width} typesets the control statement in a box % of the given \oarg{width}. % % \section{Tips and Tricks} % % A few items must be kept in mind while using this package. % Specifically, this package makes use of \textsf{everyhook} to % manipulate the |\everypar| hook. As noted % online\footnote{\url{https://tex.stackexchange.com/q/263744/61112}}, % \LaTeX{} makes extensive use of |\everypar| in many unexpected places. % From a practical point of view, the following sections point out best % practices. % % \subsection{Do Not Span Sections} % % A marking environment should not span a sectioning command. If the % document contains: % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \begin{unclassified block} % \lipsum[1] % % \chapter{The Next Chapter} % % \lipsum[2] % \end{unclassified block} % \end{lstlisting} % % the marking will be placed in the margin next to the chapter and not % associated with the chapter text. Instead, use % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \unclassified{\lipsum[1]} % % \chapter{\getmarking[1]\setlevel{1} The Next Chapter} % % \unclassified{\lipsum[2]} % \end{lstlisting} % % This will set the level, correctly associate the marking with the % chapter title, and place it in the table of contents. To silence the % warning from \textsf{hyperref}, place the macros in the \TeX{} portion % of |\texorpdfstring|. % % \subsection{Do Not Wrap Floats} % % Similar to sectioning commands, placing floating environments within a % marking block has negative consequences. When the floating % environment is placed, it will have the marking in the margin. % Instead, explicitly set the level within the floating environment and % get the marking for the caption. % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \end{unclassified block} % % \begin{figure} % \begin{secret box} % \includegraphics{example-image-16x10} % \end{secret box} % \caption{\getmarking[1] Different level caption.} % \end{figure} % % \begin{unclassified block} % \end{lstlisting} % % \subsection{Marking Front Matter Titles} % % Markings can be added to the table of contents, list of figures, and % list of tables titles using |\preto| from \textsf{etoolbox} (which is % loaded by this package). % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \AtBeginDocument{% % \preto\contentsname{\setlevel{1}\getmarking[1] } % \preto\listfigurename{\setlevel{1}\getmarking[1] } % \preto\listtablename{\setlevel{1}\getmarking[1] } % } % \end{lstlisting} % % \subsection{Marking List of Acronyms from \textsf{Acro}} % % The list of acronyms can be placed in a marking environment by % redefining the template according to example % 8\footnote{acro.example.texsx-505891} from the \textsf{acro} % documentation. % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \RenewAcroTemplate[list]{description}{% % \acroheading % \acropreamble % \begin{unclassified block} % \begin{description} % \acronymsmapF{ % \item[% % \acrowrite{short} % ] % \acrowrite{list}% % } % {\item \AcroRerun} % \end{description} % \end{unclassified block} % } % % \prinacronyms[name={\getmarking[1] \acrotranslate{list-name}}] % \end{lstlisting} % % \subsection{Adjusting Boxed Environments} % % As mentioned, the |marking box| environment relies on |tcolorbox| with % the custom |secretx| style. You may change the defaults using % |\tcbset|. The following sets all marked box titles to be bold and to % use a dark green to mark unclassified boxed content. % % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \tcbset{secretx/.append style={fonttitle=\bfseries}, % unclassified/color/.default=green!50!black, % } % \end{lstlisting} % % \StopEventually{ % \printbibliography[heading=bibnumbered] % \PrintChanges{} % \PrintIndex{} % } % % \section{Implementation} % % \iffalse %<*package> % \fi % % The basic logic is to define markings with increasing levels of % sensitivity. We track these along with paired line markings and page % markings in internal arrays. % % \subsection{Required Packages} % % For this package, we will need to modify the shipout, work with % counters, control sequences, complex labels, and we will, obviously, % need to modify the headers and footers. We add all of the packages in % one location to keep things organized. % % \begin{macrocode} \RequirePackage{atbegshi} \RequirePackage{etoolbox} \RequirePackage[excludeor]{everyhook} \RequirePackage{environ} \@ifclassloaded{beamer}{}{% \RequirePackage{fancyhdr}% } \RequirePackage{kvoptions} \RequirePackage{zref-user} \RequirePackage{zref-abspage} \@ifpackageloaded{tcolorbox}{}{% \RequirePackage{tcolorbox} } % \end{macrocode} % |Tcolorbox| moved the |\NewTColorBox| macro from the |xparse| library % in version 5.1.0. We need to include it for older versions. % \changes{v0.11}{2024/06/04}{Conditionally load xparse |tcolorbox| library} % \begin{macrocode} \@ifpackagelater{tcolorbox}{2022/06/22}{}{\tcbuselibrary{xparse}} % \end{macrocode} % % \subsection{Package Options} % % \begin{macro}{\secretx@heading} % This optional key-value pair is used to induce a manual override of % page-level headings. All pages will be marked with the indicated % heading if this option is specified. % \begin{macrocode} \DeclareStringOption{heading}[default] \ProcessKeyvalOptions* % \end{macrocode} % \end{macro} % % \subsection{Package Counters} % % Define the package counters and toggle. % % \begin{macro}{secretx@pagelevel} % A counter to store the marking level of the highest current page. % \begin{macrocode} \newcounter{secretx@pagelevel} % \end{macrocode} % \end{macro} % % \begin{macro}{secretx@doclevel} % A counter to store the highest marking level of the current document. % We also write out the document marking level to the auxiliary file for % use on the second pass when creating the cover page. % \begin{macrocode} \newcounter{secretx@doclevel} \AtEndDocument{% \immediate\write\@auxout{% \string\setcounter{secretx@doclevel}{\thesecretx@doclevel}% } } % \end{macrocode} % \end{macro} % % \begin{macro}{secretx@currentlevel} % A counter to maintain the marking level of the current scope. % \begin{macrocode} \newcounter{secretx@currentlevel} % \end{macrocode} % \end{macro} % % \begin{macro}{secretx@markcount} % A counter for the classification environment. % \begin{macrocode} \newcounter{secretx@markcount} % \end{macrocode} % \end{macro} % % \subsection{Marking and Heading Management} % % These are the user facing macros for establishing the markings and % headings. These automate away the tasks of storing the information at % increasing levels and validating the levels when getting a marking or % heading from the internal storage. When setting the marking or % heading, we simply overwrite any previous value. It is up to the user % to ensure the markings and headings are set at consistent levels. For % this, we also provide a utility macro for setting both simultaneously. % % \begin{macro}{\setmarking} % Set a marking level by defining the level and a line marking (e.g. (U) % for unclassified, (S) for secret, etc.). This will overwrite a % previously defined marking at the same level. % \begin{macrocode} \newrobustcmd{\setmarking}[2]{\csdef{secretx@marking#1}{#2}} % \end{macrocode} % \end{macro} % % \begin{macro}{\getmarking} % Get a line marking from the marking storage. % \begin{macrocode} \newrobustcmd{\getmarking}[1][\thesecretx@currentlevel]{% \ifcsdef{secretx@marking#1}{% \csuse{secretx@marking#1}% }{% \PackageWarning{secretx}{% Marking ##1 level was not previously defined. Is it a typo or did you simply forget to define it?% } } } % \end{macrocode} % \end{macro} % % \begin{macro}{\setheading} % Set the heading level by defining the level and the heading (e.g. % UNCLASSIFIED, SECRET, etc.). This will overwrite a previously defined % marking at the given level. % \begin{macrocode} \newrobustcmd{\setheading}[2]{\csdef{secretx@heading#1}{#2}} % \end{macrocode} % \end{macro} % % \begin{macro}{\getheading} % \changes{v0.11}{2023/05/23}{Get specific heading when given level} % Get the heading on the page. Use the current page level unless the % |heading| option was specified. If it was, always use it. % \begin{macrocode} \NewDocumentCommand{\getheading}{ o }{% \IfValueTF{#1}{% \ifcsdef{secretx@heading#1}{% \csuse{secretx@heading#1}% }{% \PackageError{secretx}{Undefined heading level}{% Marking ##1 level was not previously defined. Is it a typo or did you simply forget to define it?% }% }% }{% \ifdefempty{\secretx@heading}{% \csuse{secretx@heading\thesecretx@pagelevel}% }{% \ifdefstring{\secretx@heading}{default}{% % \end{macrocode} %^^A This should not be possible because the level was checked when %^^A getting the marking. % \begin{macrocode} \csuse{secretx@heading\doclevel}% }{% \csuse{secretx@heading}% }% } }% } % \end{macrocode} % \end{macro} % % \begin{macro}{\addmarking} % A helper macro to set a marking's level, section marking, and header % marking. % \begin{macrocode} \newrobustcmd{\addmarking}[3]{% \setmarking{#1}{#2}% \setheading{#1}{#3}% } % \end{macrocode} % \end{macro} % % \begin{macro}{\pagelevel} % \begin{macro}{\doclevel} % User facing macros to get the current page and document marking level. % \begin{macrocode} \newrobustcmd{\pagelevel}[0]{\thesecretx@pagelevel} \newrobustcmd{\doclevel}[0]{\thesecretx@doclevel} % \end{macrocode} % \end{macro} % \end{macro} % % \subsection{Low Level Macros} % % Some low level macros for managing the marking level state. % % \begin{macro}{\secretx@updatelevel} % A macro to update the page and document levels. We only update if the % given level is higher than the current level. We do this for both the % page and the document. % \begin{macrocode} \newrobustcmd{\secretx@updatelevel}[1]{% \ifnum#1 > \thesecretx@pagelevel% \setcounter{secretx@pagelevel}{#1}% \fi% \ifnum#1 > \thesecretx@doclevel% \setcounter{secretx@doclevel}{#1}% \fi% } % \end{macrocode} % \end{macro} % % \subsection{Marking Utilities} % % We provide a macro for marking the document. These will handle the % lower level details of getting the line markings and adjusting the % details to set the headings. Each one starts by incrementing the % marking count to track the count of the current environment, creates a % label, sets the marking for each paragraph, and inserts the content. % At the end, it sets an ending label. % % \begin{macro}{\marking} % \changes{v0.8.1}{2019/05/10}{Remove nested marking restriction} % \changes{v0.8.2}{2019/05/10}{Resolve multiply defined labels} % % The workhorse macro to actually set the headings and paragraph % markings. We begin by incrementing the current marking count and % storing it for later use. % \begin{macrocode} \newrobustcmd{\marking}[2]{% \stepcounter{secretx@markcount}% \edef\curcnt{\thesecretx@markcount}% % \end{macrocode} % Next, in order to correctly reset the level in the case of a nested % marking, we need to wrap everything up in a group and use % |\aftergroup|. But, it appears like we need to wrap the counter % setting in a macro. % \begin{macrocode} \edef\reset{% \setcounter{secretx@currentlevel}{\thesecretx@currentlevel}% }% \bgroup% \aftergroup\reset% % \end{macrocode} % Now step the environment counter to track the current environment. % \begin{macrocode} \zlabel{secretx@mark-begin-\curcnt}% \secretx@updatelevel{#1}% \setcounter{secretx@currentlevel}{#1}% #2% % \end{macrocode} % We finish by marking the ending and releasing the lock. % \begin{macrocode} \egroup% \zlabel{secretx@mark-end-\curcnt}% } % \end{macrocode} % \end{macro} % % \begin{environment}{marking block} % We also provide an environment for marking large bodies of text with a % common marking. % \begin{macrocode} \NewEnviron{marking block}[1]{\marking{#1}{\BODY}} % \end{macrocode} % \end{environment} % % \subsection{Boxed Environment Marking} % % Define a style for creating a color box with level markings in the % upper left end lower right. % \begin{macrocode} \tcbset{% secretx/.style n args={3}{% % Basic shape sharp corners,% boxrule=1pt,% boxsep=1pt,% % The heading title={\getheading[#1]},% % Place the heading in the upper left and lower right detach title, before upper={\tcbtitle\hfill\null\\[#2]},% after upper={\leavevmode\\[#3]\null\hfill\tcbtitle},% % Make the background transparent standard jigsaw,% opacityback=0.0,% % Set the default color of the heading and the frame secretx/color, }, secretx/.prefix code={\setlevel{#1}}, % Set the default color of the heading and the frame secretx/color/.default=black, secretx/color/.style={/tcb/colframe=#1,, /tcb/coltitle=#1}, } % \end{macrocode} % % \begin{macro}{marking box} % Define a new color box that passes the appropriate options to % |secretx| style. % \begin{macrocode} \NewTColorBox{marking box}{m D<>{0pt} D<>{0pt} !O{} }{% secretx={#1}{#2}{#3},% % Additional options #4% } % \end{macrocode} % \end{macro} % % \subsection{Specific Markings} % % Now we define specific markings for the known classification levels. % For each, we define an environment and a macro. % % An empty default marking. % \begin{macrocode} \addmarking{0}{}{} % \end{macrocode} % % \begin{macro}{\unclassified} % \begin{environment}{unclassified block} % Unclassified markings. % \begin{macrocode} \addmarking{1}{(U)}{Unclassified} \newrobustcmd{\unclassified}[1]{\marking{1}{#1}} \NewEnviron{unclassified block}{\unclassified{\BODY}} \tcbset{unclassified/.style 2 args={secretx={1}{#1}{#2}, unclassified/color}, unclassified/color/.forward to=/tcb/secretx/color} \NewTColorBox{unclassified box}{D<>{0pt} D<>{0pt} !O{} }{unclassified={#1}{#2}, #3} % \end{macrocode} % \end{environment} % \end{macro} % % \begin{macro}{\fouo} % \begin{environment}{fouo block} % \changes{v0.9.1}{2019/09/19}{Fix capitalization} % For official use only markings. % \begin{macrocode} \addmarking{2}{(U//FOUO)}{Unclassified//For Official Use Only} \newrobustcmd{\fouo}[1]{% \PackageWarning{secretx}{% Deprecation warning: Marking FOUO is not correct.\MessageBreak% Define and use a CUI level instead.\MessageBreak% This level will be removed in v0.11.\MessageBreak% }% \marking{2}{#1}% } \NewEnviron{fouo block}{\fouo{\BODY}} % \end{macrocode} % \end{environment} % \end{macro} % % \begin{macro}{\confidential} % \begin{environment}{confidential block} % Confidential markings. % \begin{macrocode} \addmarking{5}{(C)}{Confidential} \newrobustcmd{\confidential}[1]{\marking{5}{#1}} \NewEnviron{confidential block}{\confidential{\BODY}} \tcbset{confidential/.style 2 args={secretx={5}{#1}{#2}, confidential/color}, confidential/color/.forward to=/tcb/secretx/color} \NewTColorBox{confidential box}{D<>{0pt} D<>{0pt} !O{} }{confidential={#1}{#2}, #3} % \end{macrocode} % \end{environment} % \end{macro} % % \begin{macro}{\secret} % \begin{environment}{secret block} % Secret markings. % \begin{macrocode} \addmarking{10}{(S)}{Secret} \newrobustcmd{\secret}[1]{\marking{10}{#1}} \NewEnviron{secret block}{\secret{\BODY}} \tcbset{secret/.style 2 args={secretx={10}{#1}{#2}, confidential/color}, secret/color/.forward to=/tcb/secretx/color} \NewTColorBox{secret box}{D<>{0pt} D<>{0pt} !O{} }{secret={#1}{#2}, #3} % \end{macrocode} % \end{environment} % \end{macro} % % \begin{macro}{\secretnoforn} % \begin{environment}{secretnoforn block} % Secret no forn markings. % \begin{macrocode} \addmarking{15}{(S//NF)}{Secret//No Forn} \newrobustcmd{\secretnoforn}[1]{\marking{15}{#1}} \NewEnviron{secretnoforn block}{\secretnoforn{\BODY}} \tcbset{secretnoforn/.style 2 args={secretx={15}{#1}{#2}, secretnoforn/color}, secretnoforn/color/.forward to=/tcb/secretx/color} \NewTColorBox{secretnoforn box}{D<>{0pt} D<>{0pt} !O{} }{secretnoforn={#1}{#2}, #3} % \end{macrocode} % \end{environment} % \end{macro} % % \begin{macro}{\topsecret} % \begin{environment}{topsecret block} % Top secret markings. % \begin{macrocode} \addmarking{25}{(TS)}{Top Secret} \newrobustcmd{\topsecret}[1]{\marking{25}{#1}} \NewEnviron{topsecret block}{\topsecret{\BODY}} \tcbset{topsecret/.style 2 args={secretx={25}{#1}{#2}, topsecret/color}, topsecret/color/.forward to=/tcb/secretx/color} \NewTColorBox{topsecret box}{D<>{0pt} D<>{0pt} !O{} }{topsecret={#1}{#2}, #3} % \end{macrocode} % \end{environment} % \end{macro} % % \subsection{Overriding the Default Page Marking} % % \begin{macro}{\setlevel} % This macro provides a user interface to explicitly set the page level. % It is targeted as \textsf{beamer} frames that are predominantly % explicitly marked. % \begin{macrocode} \newrobustcmd{\setlevel}[1]{% \secretx@updatelevel{#1}% } % \end{macrocode} % \end{macro} % % \subsection{Deprecated Macros} % % \begin{notice} % These macros will be removed in v0.11. % \end{notice} % These macros are deprecated and are preserved for temporary backwards % compatibility. They will be removed in the future. % % \begin{macrocode} \newrobustcmd{\UCL}[1]{% \PackageWarning{secretx}{Macro deprecated! Use \protect\unclassified\space instead}% \unclassified{#1}% } \newrobustcmd{\CNF}[1]{% \PackageWarning{secretx}{Macro deprecated! Use \\protect\confidential\space instead}% \confidential{#1}% } \newrobustcmd{\SEC}[1]{% \PackageWarning{secretx}{Macro deprecated! Use \\protect\secret\space instead}% \secret{#1}% } \newrobustcmd{\SNF}[1]{% \PackageWarning{secretx}{Macro deprecated! Use \\protect\secretnoforn\space instead}% \secretnoforn{#1}% } \newrobustcmd{\TS}[1]{% \PackageWarning{secretx}{Macro deprecated! Use \\protect\topsecret\space instead}% \topsecret{#1}% } % \end{macrocode} % % \subsection{Formatting Details} % % Now we move on to specific formatting details. The header and footer % are determined by the marking level of the current page, but only for % article style documents and not beamer slides. For beamer, we need to % provide a headline and footline template. We can use our macros to % set them once. We only specify the center header and footer and leave % the left and right marks up to the user. % % For \textsf{beamer}, simply use % \begin{lstlisting}[gobble=2, basicstyle=\ttfamily\small] % \usebeamertemplate{headline}[secretx] % \usebeamertemplate{footline}[secretx] % \end{lstlisting} % to get a centered marking on the header and footer. To customize your % headline and footline, simply add |\getheading| to your template. % See~\cref{app:beamer} for a simple example. % % \changes{v0.8.4}{2019/05/11}{Provide beamer head/footline} % \changes{v0.8.7}{2019/10/17}{Adjust beamer header/footer to keep size} % \changes{v0.11}{2024/06/20}{Allow selecting the document level for header/footer} % \begin{macrocode} \@ifclassloaded{beamer}{% \defbeamertemplate*{headline}{secretx}[1][]{% \begin{beamercolorbox}[ht=5ex]{headline} \usebeamerfont{secretx}\hfill% \ifstrequal{#1}{title}{\getheading[\doclevel]}{\getheading}% \hfill\null% \end{beamercolorbox} } \defbeamertemplate*{footline}{secretx}[1][]{% \begin{beamercolorbox}[ht=6ex]{footline} \usebeamerfont{secretx}\hfill% \ifstrequal{#1}{title}{\getheading[\doclevel]}{\getheading}% \hfill\null\vspace{3pt}% \end{beamercolorbox} } \setbeamerfont{secretx}{size=\Large,% series=\bfseries,% parent=structure} }{% \fancypagestyle{secretx}{% \fancyhead[C]{\getheading} \fancyfoot[C]{\getheading} } \pagestyle{secretx} } % \end{macrocode} % % \changes{v0.7.2}{2019/05/03}{Use everyhook to mark paragraphs} % \changes{v0.8.3}{2019/05/10}{Use PushPostHook for everypar} % \changes{v0.10}{2022/11/22}{Do not overhang the margin} % \changes{v0.11}{2023/05/22}{Aim for the margin using everyhook's % recommended method.} % We also place the marking before every paragraph based on the current % marking level. % \begin{macrocode} \PushPreHook{par}{% \ifcsempty{secretx@marking\thesecretx@currentlevel}% {}{\setbox0=\lastbox\llap{\getmarking{}% \hspace{5pt}% \hspace{\secretx@listmargin}}% \box0}% } % \end{macrocode} % % And now we need to deal with resetting the page levels correctly. % Each marking has been placed between begin and end labels. We can % check the last label when a page ships out to see if the begin is on % the same page. If it is not, we need to preserve the page level on % the next page. Otherwise, we need to reset the page to empty. % % \begin{macrocode} \AtBeginShipout{% \ifnum\zref@extract{secretx@mark-begin-\thesecretx@markcount}{abspage} =\zref@extract{secretx@mark-end-\thesecretx@markcount}{abspage} \setcounter{secretx@pagelevel}{0}% \else% \setcounter{secretx@pagelevel}{\thesecretx@currentlevel}% \fi% } % \end{macrocode} % % \begin{macro}{secretx@listlevel} % \changes{v0.11}{2023/05/22}{Add list counter for margins} % This counter is used to determine the nesting of the list level. It % will be used to determine if the current paragraph is within a noted % list environment to return the correct padding. We hook into each % known list environment\footnote{This could be done with \LaTeX3 using % \href{https://tex.stackexchange.com/a/638275/61112}{AddToHook}, but % that is a \href{https://tex.stackexchange.com/q/602066/61112}{recent % addition}.}. % \begin{macrocode} \newcounter{secretx@listlevel} \setcounter{secretx@listlevel}{0} \AtBeginEnvironment{itemize}{\addtocounter{secretx@listlevel}{1}} \AtEndEnvironment{itemize}{\addtocounter{secretx@listlevel}{-1}} \AtBeginEnvironment{enumerate}{\addtocounter{secretx@listlevel}{1}} \AtEndEnvironment{enumerate}{\addtocounter{secretx@listlevel}{-1}} \AtBeginEnvironment{description}{\addtocounter{secretx@listlevel}{1}} \AtEndEnvironment{description}{\addtocounter{secretx@listlevel}{-1}} % \end{macrocode} % \end{macro} % % \begin{macro}{secretx@listmargin} % \changes{v0.11}{2023/05/22}{Define margin macro for markings lists} % This defines an additional offset for list environments to make sure % the marking does not overhang the label. % \begin{macrocode} \newrobustcmd\secretx@listmargin[0]{% \ifnumgreater{\value{secretx@listlevel}}{0}{\leftmargin}{0pt} } % \end{macrocode} % \end{macro} % % \subsection{Additional Statements} % \changes{v0.10}{2021/03/14}{Add distribution statements} % % \begin{macro}{\distribution} % Define the wrapper for directing to the proper distribution statement. % \begin{macrocode} \newrobustcmd\distribution[4]{% DISTRIBUTION STATEMENT #1. \csuse{secretx@distro@#1}{#2}{#3}{#4}% } % \end{macrocode} % The individual statements from Table 5 in \cite{dodi_5230.24}. % \begin{macrocode} \newrobustcmd\secretx@distro@A[3]{% Approved for public release: distribution unlimited. } \newrobustcmd\secretx@distro@B[3]{% Distribution authorized to U.S. Government agencies #1 #2. Other requests for this document shall be referred to #3. } \newrobustcmd\secretx@distro@C[3]{% Distribution authorized to U.S. Government agencies and their contractors #1 #2. Other requests for this document shall be referred to #3. } \newrobustcmd\secretx@distro@D[3]{% Distribution authorized to Department of Defense and U.S. DoD contractors only #1 #2. Other requests for this document shall be referred to #3. } \newrobustcmd\secretx@distro@E[3]{% Distribution authorized to DoD Components only #1 #2. Other requests for this document shall be referred to #3. } \newrobustcmd\secretx@distro@F[3]{% Further dissemination only as directed by #3 #2 or higher DoD authority. } % \end{macrocode} % \end{macro} % % \begin{macro}{\exportcontrol} % \changes{v0.10}{2021/03/14}{Add export control statement} % % Typeset the export control statement in a framed box. % \begin{macrocode} \newrobustcmd\exportcontrol[1][0.9\textwidth]{ \fbox{% \begin{minipage}{#1}% WARNING - This document contains technical data whose export is restricted by the Arms Export Control Act (Title 22, U.S.C., Sec 2751, et seq.) or the Export Administration Act of 1979 (Title 50, U.S.C., App. 2401 et seq.), as amended. Violations of these export laws are subject to severe criminal penalties. Disseminate in accordance with provisions of DoD Directive 5230.25. \end{minipage}% }% } % \end{macrocode} % \end{macro} % % \iffalse % % \fi % % \appendix % % \section{\label{app:example} Examples} % % This is the code demonstrating the use of \textsf{secretx}. The % source is in the \textsf{doc/latex/secretx} directory. Simply run the % code through \LaTeX{} to see the typeset examples. % % \subsection{\label{app:document} Example Document} % \changes{v0.8.4}{2019/05/11}{Move example article to appendix} % % \begin{lstlisting}[basicstyle=\ttfamily\small] % \iffalse %<*document> % \fi \documentclass{article} \usepackage{secretx} \title{\unclassified{An example document with markings}} \author{Keith F. Prussing} \date{\today} % Show the page and document level in the header. \fancyhead[L]{Document --- \doclevel} \fancyhead[R]{Page --- \pagelevel} \fancyfoot[L]{\thepage} % Remove the header line. \renewcommand{\headrulewidth}{0pt} % Redefine headers and markings to avoid unnecessary alarm. \addmarking{1}{(1)}{Trivial} \addmarking{5}{(5)}{Sensitive} \addmarking{10}{(10)}{Important} \addmarking{25}{(25)}{Very Important} \usepackage{mwe} \usepackage[colorlinks]{hyperref} \begin{document} \maketitle \thispagestyle{secretx} \tableofcontents \listoffigures \begin{abstract} \unclassified{% This is an example document showing the usage of the \textsf{secretx} package. The markings in the following are purely for demonstration purpose. All of the material is unclassified.\footnote{\unclassified{% This document may have been typeset with the markings adjusted to prevent unnecessary alarm. To see the real markings, simply remove the redefinitions as described in \href{file://secretx.pdf}{secretx.pdf} and rerun through \LaTeX{}. } } } \end{abstract} \unclassified{\lipsum[1]}\par \unclassified{\lipsum[2]}\par \unclassified{\lipsum[3]}\par \confidential{\lipsum[4]}\par \unclassified{\lipsum[5]}\par \unclassified{\lipsum[6]}\par \topsecret{\lipsum[7]}\par \secret{\lipsum[8]}\par \section{\setlevel{1}\getmarking[1] A New Section} \unclassified{\lipsum[9]\par\secret{\lipsum[9]\par}\lipsum[9]}\par \unclassified{\lipsum[10]}\par \unclassified{\lipsum[11]}\par \unclassified{\lipsum[12]}\par \unclassified{\lipsum[13]}\par \unclassified{\lipsum[14]}\par \unclassified{\lipsum[15]}\par % Demonstrate marking a figure. \begin{figure} \centering \begin{secret box} \includegraphics{example-image-16x10}% \end{secret box} \caption{\setlevel{1}\getmarking[1]% An example image with a classification on the caption. } \end{figure} % Use as an environment \begin{unclassified block} \lipsum[16-20] \end{unclassified block} \begin{secret block} \section{A Section within a Block} Notice how the marking gets placed in the margin and not correctly with the section title? It is not properly reflected in the table of contents. Additionally, Fig. \ref{fig:bad-figure} places the markings in the margin and not with the image or the caption. \lipsum[21]\par \unclassified{\lipsum[22]}\par \lipsum[23]\par \begin{figure} \includegraphics{example-image-16x10} \unclassified{\caption{A short caption}} \label{fig:bad-figure} \end{figure} \end{secret block} \begin{itemize} \item \unclassified{The first unclassified item} \item \confidential{The second item is a higher marking} \item \unclassified{The third is back to unclassified} \end{itemize} \unclassified{\lipsum[1]\par} \begin{enumerate} \item \confidential{First enumerated item} \item \unclassified{A second enumerated item} \item \unclassified{And a final enumerated item} \end{enumerate} \begin{description} \item[One] \unclassified{First description item} \item[Two] \unclassified{A second description item} \item[Three] \confidential{And a final description item} \end{description} \end{document} % \iffalse % % \fi % \end{lstlisting} % % \subsection{\label{app:beamer} Beamer Slides} % \changes{v0.8.4}{2019/05/11}{Add beamer example} % % \begin{lstlisting}[basicstyle=\ttfamily\small] % \iffalse %<*slides> % \fi \documentclass{beamer} \usepackage{secretx} \begin{document} \begin{frame} \frametitle{\unclassified{An example}} \begin{itemize} \item \unclassified{An unclassified item} \end{itemize} \end{frame} \begin{frame} \frametitle{\unclassified{A slide with secret information}} \begin{itemize} \item \secret{A secret item} \end{itemize} \end{frame} \end{document} % \iffalse % % \fi % \end{lstlisting} % % \Finale{} % % \iffalse %<*bibliography> @manual{dodi_5230.24, title = {{Distribution} {Statements} on {Technical} {Documents}}, editor = {Frank Kendall}, type = {{DoD} {Instruction}}, number = 5230.24, year = 2018, month = 10, day = 15, organization = {{Department} of {Defense}}, location = {Washington, DC}, url = {https://www.esd.whs.mil/Portals/54/Documents/DD/issuances/dodi/523024p.pdf}, urldate = {2021-03-13} } @misc{noauthor_marking_2021, title = {Marking {Classified} {Information} {Job} {Aid}}, url = {https://www.cdse.edu/Portals/124/Documents/jobaids/information/Marking_Classified_Information.pdf?ver=K6RVqlnVuvTyO5lI2yF23g%3d%3d}, urldate = {2022-11-28}, publisher = {Center for Development of Security Excellence}, month = jul, year = {2021}, } % % \fi % \endinput