% \iffalse meta-comment % %% File: l3bootstrap.dtx Copyright (C) 2011-2014 The LaTeX3 project %% %% It may be distributed and/or modified under the conditions of the %% LaTeX Project Public License (LPPL), either version 1.3c of this %% license or (at your option) any later version. The latest version %% of this license is in the file %% %% http://www.latex-project.org/lppl.txt %% %% This file is part of the "l3kernel bundle" (The Work in LPPL) %% and all files in that bundle must be distributed together. %% %% The released version of this bundle is available from CTAN. %% %% ----------------------------------------------------------------------- %% %% The development version of the bundle can be found at %% %% http://www.latex-project.org/svnroot/experimental/trunk/ %% %% for those people who are interested. %% %%%%%%%%%%% %% NOTE: %% %%%%%%%%%%% %% %% Snapshots taken from the repository represent work in progress and may %% not work or may contain conflicting material! We therefore ask %% people _not_ to put them into distributions, archives, etc. without %% prior consultation with the LaTeX3 Project. %% %% ----------------------------------------------------------------------- % %<*driver|package> % \begin{macro}{\GetIdInfo} % \begin{macro}[aux]{\GetIdInfoAuxI, \GetIdInfoAuxII, \GetIdInfoAuxIII} % The idea here is to extract out the information needed from a standard % \textsc{svn} \texttt{Id} line, but without a line that will get % changed when the file is checked in. Hence the fact that there is % not a line which includes both a dollar sign and the \texttt{Id} % keyword together! % \begin{macrocode} \protected\def\GetIdInfo {% \begingroup \catcode 32 = 10 % \GetIdInfoAuxI } % \end{macrocode} % A first check for a completely empty \textsc{svn} field. If that is % not the case, there is a second case when a file created using % \texttt{svn cp} but has not been checked in. That leaves a special % marker \texttt{-1} version, which has no further data. Dealing correctly % with that is the reason for the space in the line to use % \cs{GetIdInforAuxII}. % \begin{macrocode} \protected\def\GetIdInfoAuxI$#1$#2% {% \def\tempa{#1}% \def\tempb{Id}% \ifx\tempa\tempb \def\tempa {% \endgroup \def\ExplFileDate{9999/12/31}% \def\ExplFileDescription{#2}% \def\ExplFileName{[unknown name]}% \def\ExplFileExtension{[unknown extension]}% \def\ExplFileVersion{999}% }% \else \def\tempa {% \endgroup \def\ExplFileDescription{#2}% \GetIdInfoAuxII$#1 $% }% \fi \tempa } % \end{macrocode} % Here, |#1| is |Id|, |#2| is the file name, |#3| is the extension, % |#4| is the version, |#5| is the check in date and |#6| is the check in % time and user, plus some trailing spaces. If |#4| is the marker |-1| value % then |#5| and |#6| will be empty. % \begin{macrocode} \protected\def\GetIdInfoAuxII$#1 #2.#3 #4 #5 #6$% {% \def\ExplFileName{#2}% \def\ExplFileExtension{#3}% \def\ExplFileVersion{#4}% \begingroup \def\tempa{#4}% \def\tempb{-1}% \ifx\tempa\tempb \def\tempa {% \endgroup \def\ExplFileDate{0000/00/00}% }% \else \def\tempa {% \endgroup \GetIdInfoAuxIII$#5$% }% \fi \tempa } % \end{macrocode} % Convert an \textsc{svn}-style date into a \LaTeX{}-style one. % \begin{macrocode} \protected\def\GetIdInfoAuxIII$#1-#2-#3$% {% \def\ExplFileDate{#1/#2/#3}% } % \end{macrocode} % \end{macro} % \end{macro} \GetIdInfo$Id: l3bootstrap.dtx 4640 2014-01-04 16:03:52Z joseph $ {L3 Bootstrap code} % %<*driver> \documentclass[full]{l3doc} \begin{document} \DocInput{\jobname.dtx} \end{document} % % \fi % % \title{^^A % The \pkg{l3bootstrap} package\\ Bootstrap code^^A % \thanks{This file describes v\ExplFileVersion, % last revised \ExplFileDate.}^^A % } % % \author{^^A % The \LaTeX3 Project\thanks % {^^A % E-mail: % \href{mailto:latex-team@latex-project.org} % {latex-team@latex-project.org}^^A % }^^A % } % % \date{Released \ExplFileDate} % % \maketitle % % \begin{documentation} % % \section{Using the \LaTeX3 modules} % % The modules documented in \file{source3} are designed to be used on top of % \LaTeXe{} and are loaded all as one with the usual |\usepackage{expl3}| or % |\RequirePackage{expl3}| instructions. These modules will also form the % basis of the \LaTeX3 format, but work in this area is incomplete and not % included in this documentation at present. % % As the modules use a coding syntax different from standard % \LaTeXe{} it provides a few functions for setting it up. % % \begin{function}[updated = 2011-08-13]{\ExplSyntaxOn, \ExplSyntaxOff} % \begin{syntax} % \cs{ExplSyntaxOn} \meta{code} \cs{ExplSyntaxOff} % \end{syntax} % The \cs{ExplSyntaxOn} function switches to a category code % r\'{e}gime in which spaces are ignored and in which the colon (|:|) % and underscore (|_|) are treated as \enquote{letters}, thus allowing % access to the names of code functions and variables. Within this % environment, |~| is used to input a space. The \cs{ExplSyntaxOff} % reverts to the document category code r\'{e}gime. % \end{function} % % \begin{function}{\ProvidesExplPackage, \ProvidesExplClass, \ProvidesExplFile} % \begin{syntax} % |\RequirePackage{expl3}| \\ % \cs{ProvidesExplPackage} \Arg{package} \Arg{date} \Arg{version} \Arg{description} % \end{syntax} % These functions act broadly in the same way as the \LaTeXe{} kernel % functions \cs{ProvidesPackage}, \cs{ProvidesClass} and % \cs{ProvidesFile}. However, they also implicitly switch % \cs{ExplSyntaxOn} for the remainder of the code with the file. At the % end of the file, \cs{ExplSyntaxOff} will be called to reverse this. % (This is the same concept as \LaTeXe{} provides in turning on % \tn{makeatletter} within package and class code.) % \end{function} % % \begin{function}[updated = 2012-06-04]{\GetIdInfo} % \begin{syntax} % |\RequirePackage{l3bootstrap}| % \cs{GetIdInfo} |$Id:| \meta{SVN info field} |$| \Arg{description} % \end{syntax} % Extracts all information from a SVN field. Spaces are not % ignored in these fields. The information pieces are stored in % separate control sequences with \cs{ExplFileName} for the part of the % file name leading up to the period, \cs{ExplFileDate} for date, % \cs{ExplFileVersion} for version and \cs{ExplFileDescription} for the % description. % \end{function} % % To summarize: Every single package using this syntax should identify % itself using one of the above methods. Special care is taken so that % every package or class file loaded with \tn{RequirePackage} or alike % are loaded with usual \LaTeXe{} category codes and the \LaTeX3 category code % scheme is reloaded when needed afterwards. See implementation for % details. If you use the \cs{GetIdInfo} command you can use the % information when loading a package with % \begin{verbatim} % \ProvidesExplPackage{\ExplFileName} % {\ExplFileDate}{\ExplFileVersion}{\ExplFileDescription} % \end{verbatim} % % \subsection{Internal functions and variables} % % \begin{function}{\__expl_package_check:} % \begin{syntax} % \cs{__expl_package_check:} % \end{syntax} % Used to ensure that all parts of \pkg{expl3} are loaded together % (\emph{i.e.}~as part of \pkg{expl3}). Issues an error if a kernel package % is loaded independently of the bundle. % \end{function} % % \begin{variable}{\l__kernel_expl_bool} % A boolean which records the current code syntax status: \texttt{true} if % currently inside a code environment. This variable should only be % set by \cs{ExplSyntaxOn}/\cs{ExplSyntaxOff}. % \end{variable} % % \end{documentation} % % \begin{implementation} % % \section{\pkg{l3bootstrap} implementation} % % \begin{macrocode} %<*initex|package> %<@@=expl> % \end{macrocode} % % \subsection{Format-specific code} % % The very first thing to do is to bootstrap the \IniTeX{} system so % that everything else will actually work. \TeX{} does not start with % some pretty basic character codes set up. % \begin{macrocode} %<*initex> \catcode `\{ = 1 \relax \catcode `\} = 2 \relax \catcode `\# = 6 \relax \catcode `\^ = 7 \relax % % \end{macrocode} % % Tab characters should not show up in the code, but to be on the % safe side. % \begin{macrocode} %<*initex> \catcode `\^^I = 10 \relax % % \end{macrocode} % % For \LuaTeX{} the extra primitives need to be enabled before % they can be used. No \tn{ifdefined} yet, so do it the old-fashioned % way. The primitive \tn{strcmp} is simulated using some \Lua{} % code, which currently has to be applied to every job as the \Lua{} % code is not part of the format. Thanks to Taco Hoekwater for this % code. The odd \tn{csname} business is needed so that the later % deletion code will work. % \begin{macrocode} %<*initex> \begingroup\expandafter\expandafter\expandafter\endgroup \expandafter\ifx\csname directlua\endcsname\relax \else \directlua { tex.enableprimitives('',tex.extraprimitives ()) lua.bytecode[1] = function () function strcmp (A, B) if A == B then tex.write("0") elseif A < B then tex.write("-1") else tex.write("1") end end end lua.bytecode[1]() } \everyjob\expandafter {\csname\detokenize{luatex_directlua:D}\endcsname{lua.bytecode[1]()}} \long\edef\pdfstrcmp#1#2% {% \expandafter\noexpand\csname\detokenize{luatex_directlua:D}\endcsname {% strcmp% (% "\noexpand\luaescapestring{#1}",% "\noexpand\luaescapestring{#2}"% )% }% } \fi % % \end{macrocode} % % \subsection{Package-specific code part one} % % The package starts by identifying itself: the information itself is % taken from the SVN |Id| string at the start of the source file. % \begin{macrocode} %<*package> \ProvidesPackage{l3bootstrap} [% \ExplFileDate\space v\ExplFileVersion\space L3 Experimental bootstrap code% ] % % \end{macrocode} % % For \LuaTeX{} the functionality of the \tn{pdfstrcmp} primitive % needs to be provided: the \pkg{pdftexmcds} package is used to % do this if necessary. At present, there is also a need to deal % with some low-level allocation stuff that could usefully be added % to \texttt{lualatex.ini}. As it is currently not, load Heiko % Oberdiek's \pkg{luatex} package instead. % \begin{macrocode} %<*package> \begingroup\expandafter\expandafter\expandafter\endgroup \expandafter\ifx\csname directlua\endcsname\relax \else \begingroup \def\@tempa {% \endgroup \RequirePackage{luatex}% \RequirePackage{pdftexcmds}% }% \expandafter\@tempa \fi % % \end{macrocode} % % \subsection{The \tn{pdfstrcmp} primitive in \XeTeX{}} % % Only \pdfTeX{} has a primitive called \tn{pdfstrcmp}. The \XeTeX{} % version is just \tn{strcmp}, so there is some shuffling to do. As % this is still a real primitive, using the \pdfTeX{} name is \enquote{safe}. % \begin{macrocode} \begingroup\expandafter\expandafter\expandafter\endgroup \expandafter\ifx\csname pdfstrcmp\endcsname\relax \let\pdfstrcmp\strcmp \fi % \end{macrocode} % % \subsection{Engine requirements} % % The code currently requires functionality equivalent to \tn{pdfstrcmp} % in addition to \eTeX{}. In package mode, there is the slight caveat that % with \LuaTeX{} emulating this primitive is be done using a different % name as the expansion behaviour is different. % \begin{macrocode} \begingroup \def\ShortText{Required primitives not found}% \def\LongText% {% LaTeX3 requires the e-TeX primitives and \string\pdfstrcmp.\LineBreak \LineBreak These are available in engine versions:\LineBreak - pdfTeX 1.30\LineBreak - XeTeX 0.9994\LineBreak - LuaTeX 0.40\LineBreak or later.\LineBreak \LineBreak }% \expandafter\ifx\csname pdfstrcmp\endcsname\relax %<*initex> \def\LineBreak{^^J}% \edef\Error% {% \endgroup \newlinechar`\noexpand\^^J\relax \errhelp {% \LongText For pdfTeX and XeTeX the '-etex' command-line switch is also needed.\LineBreak \LineBreak Format building will abort!\LineBreak }% \errmessage{\ShortText}% \noexpand\end }% \expandafter\Error % %<*package> \expandafter\ifx\csname pdf@strcmp\endcsname\relax \def\LineBreak{\noexpand\MessageBreak}% \edef\Error% {% \endgroup \noexpand\PackageError{expl3}{\ShortText} {\LongText Loading of expl3 will abort!}% \noexpand\endinput }% \expandafter\expandafter\expandafter\Error \else \endgroup \fi % \else \endgroup \fi % \end{macrocode} % % \subsection{Package-specific code part two} % % \begin{macro}{\ExplSyntaxOff, \ExplSyntaxOn} % Experimental syntax switching is set up here for the package-loading % process. These are redefined in \pkg{expl3} for the package and in % \pkg{l3final} for the format. % \begin{macrocode} %<*package> \protected\edef\ExplSyntaxOff {% \catcode 9 = \the\catcode 9\relax \catcode 32 = \the\catcode 32\relax \catcode 34 = \the\catcode 34\relax \catcode 38 = \the\catcode 38\relax \catcode 58 = \the\catcode 58\relax \catcode 94 = \the\catcode 94\relax \catcode 95 = \the\catcode 95\relax \catcode 124 = \the\catcode 124\relax \catcode 126 = \the\catcode 126\relax \endlinechar = \the\endlinechar\relax \chardef\csname\detokenize{l__kernel_expl_bool}\endcsname = 0 \relax } \protected\edef\ExplSyntaxOn {% \catcode 9 = 9 \relax \catcode 32 = 9 \relax \catcode 34 = 12 \relax \catcode 58 = 11 \relax \catcode 94 = 7 \relax \catcode 95 = 11 \relax \catcode 124 = 12 \relax \catcode 126 = 10 \relax \endlinechar = 32 \relax \chardef\csname\detokenize{l__kernel_expl_bool}\endcsname = 1 \relax } % % \end{macrocode} % \end{macro} % % \begin{variable}{\l__kernel_expl_bool} % The status for experimental code syntax: this is off at present. This % code is used by both the package and the format. % \begin{macrocode} \expandafter\chardef\csname\detokenize{l__kernel_expl_bool}\endcsname = 0 \relax % \end{macrocode} %\end{variable} % % \subsection{Dealing with package-mode meta-data} % % \begin{macro}{\GetIdInfo} % This is implemented right at the start of \texttt{l3bootstrap.dtx}. % \end{macro} % % \begin{macro}{\ProvidesExplPackage, \ProvidesExplClass, \ProvidesExplFile} % For other packages and classes building on this one it is convenient % not to need \cs{ExplSyntaxOn} each time. % \begin{macrocode} %<*package> \protected\def\ProvidesExplPackage {% \@ifpackageloaded{expl3} {} {% \PackageError{expl3} {Cannot load the expl3 modules separately} {% The expl3 modules cannot be loaded separately;\MessageBreak please \string\usepackage\string{expl3\string} instead.% }% }% \protected\def\ProvidesExplPackage##1##2##3##4% {% \ProvidesPackage{##1}[##2 v##3 ##4]% \ExplSyntaxOn }% \ProvidesExplPackage } \protected\def\ProvidesExplClass#1#2#3#4% {% \ProvidesClass{#1}[#2 v#3 #4]% \ExplSyntaxOn } \protected\def\ProvidesExplFile#1#2#3#4% {% \ProvidesFile{#1}[#2 v#3 #4]% \ExplSyntaxOn } % % \end{macrocode} % \end{macro} % % \begin{macro}{\@pushfilename, \@popfilename} % The idea here is to use \LaTeXe{}'s \tn{@pushfilename} and % \tn{@popfilename} to track the current syntax status. This can be % achieved by saving the current status flag at each push to a stack, % then recovering it at the pop stage and checking if the code % environment should still be active. % \begin{macrocode} %<*package> \edef\@pushfilename {% \edef\expandafter\noexpand \csname\detokenize{l_@@_status_stack_tl}\endcsname {% \noexpand\ifodd\expandafter\noexpand \csname\detokenize{l__kernel_expl_bool}\endcsname 1% \noexpand\else 0% \noexpand\fi \expandafter\noexpand \csname\detokenize{l_@@_status_stack_tl}\endcsname }% \ExplSyntaxOff \unexpanded\expandafter{\@pushfilename}% } \edef\@popfilename {% \unexpanded\expandafter{\@popfilename}% \noexpand\if a\expandafter\noexpand\csname \detokenize{l_@@_status_stack_tl}\endcsname a% \ExplSyntaxOff \noexpand\else \noexpand\expandafter \expandafter\noexpand\csname \detokenize{@@_status_pop:w}\endcsname \expandafter\noexpand\csname \detokenize{l_@@_status_stack_tl}\endcsname \noexpand\@nil \noexpand\fi } % % \end{macrocode} % \end{macro} % % \begin{macro}{\l_@@_status_stack_tl} % As \pkg{expl3} itself cannot be loaded with the code environment % already active, at the end of the package \cs{ExplSyntaxOff} can % safely be called. % \begin{macrocode} %<*package> \@namedef{\detokenize{l_@@_status_stack_tl}}{0} % % \end{macrocode} % \end{macro} % % \begin{macro}[aux]{\@@_status_pop:w} % The pop auxiliary function removes the first item from the stack, % saves the rest of the stack and then does the test. As % \cs{ExplSyntaxOff} is already defined as a protected macro, there % is no need for \tn{noexpand} here. % \begin{macrocode} %<*package> \expandafter\edef\csname\detokenize{@@_status_pop:w}\endcsname#1#2\@nil {% \def\expandafter\noexpand \csname\detokenize{l_@@_status_stack_tl}\endcsname{#2}% \noexpand\ifodd#1\space \noexpand\expandafter\noexpand\ExplSyntaxOn \noexpand\else \noexpand\expandafter\ExplSyntaxOff \noexpand\fi } % % \end{macrocode} % \end{macro} % % \begin{macro}[int]{\__expl_package_check:} % We want the \pkg{expl3} bundle to be loaded \enquote{as one}; % this command is used to ensure that one of the |l3| packages isn't loaded % on its own. % \begin{macrocode} %<*package> \expandafter\protected\expandafter\def \csname\detokenize{__expl_package_check:}\endcsname {% \@ifpackageloaded{expl3} {} {% \PackageError{expl3} {Cannot load the expl3 modules separately} {% The expl3 modules cannot be loaded separately;\MessageBreak please \string\usepackage\string{expl3\string} instead.% }% }% } % % \end{macrocode} % \end{macro} % % \subsection{The \LaTeX3 code environment} % % The code environment is now set up for the format: the package deals % with this using \cs{ProvidesExplPackage}. % \begin{macrocode} %<*initex> \catcode 9 = 9 \relax \catcode 32 = 9 \relax \catcode 34 = 12 \relax \catcode 58 = 11 \relax \catcode 94 = 7 \relax \catcode 95 = 11 \relax \catcode 124 = 12 \relax \catcode 126 = 10 \relax \endlinechar = 32 \relax % % \end{macrocode} % % \begin{macro}{\ExplSyntaxOn, \ExplSyntaxOff} % The idea here is that multiple \cs{ExplSyntaxOn} calls are not % going to mess up category codes, and that multiple calls to % \cs{ExplSyntaxOff} are also not wasting time. % \begin{macrocode} %<*initex> \protected \def \ExplSyntaxOn { \bool_if:NF \l__kernel_expl_bool { \cs_set_protected_nopar:Npx \ExplSyntaxOff { \char_set_catcode:nn { 9 } { \char_value_catcode:n { 9 } } \char_set_catcode:nn { 32 } { \char_value_catcode:n { 32 } } \char_set_catcode:nn { 34 } { \char_value_catcode:n { 34 } } \char_set_catcode:nn { 38 } { \char_value_catcode:n { 38 } } \char_set_catcode:nn { 58 } { \char_value_catcode:n { 58 } } \char_set_catcode:nn { 94 } { \char_value_catcode:n { 94 } } \char_set_catcode:nn { 95 } { \char_value_catcode:n { 95 } } \char_set_catcode:nn { 124 } { \char_value_catcode:n { 124 } } \char_set_catcode:nn { 126 } { \char_value_catcode:n { 126 } } \tex_endlinechar:D = \tex_the:D \tex_endlinechar:D \scan_stop: \bool_set_false:N \l__kernel_expl_bool \cs_set_protected_nopar:Npn \ExplSyntaxOff { } } } \char_set_catcode_ignore:n { 9 } % tab \char_set_catcode_ignore:n { 32 } % space \char_set_catcode_other:n { 34 } % double quote \char_set_catcode_alignment:n { 38 } % ampersand \char_set_catcode_letter:n { 58 } % colon \char_set_catcode_math_superscript:n { 94 } % circumflex \char_set_catcode_letter:n { 95 } % underscore \char_set_catcode_other:n { 124 } % pipe \char_set_catcode_space:n { 126 } % tilde \tex_endlinechar:D = 32 \scan_stop: \bool_set_true:N \l__kernel_expl_bool } \protected \def \ExplSyntaxOff { } % % \end{macrocode} % \end{macro} % % \begin{variable}{\l__kernel_expl_bool} % A flag to show the current syntax status. % \begin{macrocode} %<*initex> \chardef \l__kernel_expl_bool = 0 ~ % % \end{macrocode} % \end{variable} % % \begin{macrocode} % % \end{macrocode} % % \end{implementation} % % \PrintIndex