% \iffalse
%% File: l3quark.dtx Copyright (C) 1990-2009 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 ``expl3 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 LaTeX Project Team.
%%
%% -----------------------------------------------------------------------
%
%<*driver|package>
\RequirePackage{l3names}
%</driver|package>
%\fi
\GetIdInfo$Id: l3quark.dtx 2172 2011-03-03 10:56:49Z will $
          {L3 Experimental Quark Commands}
%\iffalse
%<*driver>
%\fi
\ProvidesFile{\filename.\filenameext}
  [\filedate\space v\fileversion\space\filedescription]
%\iffalse
\documentclass[full,checktest]{l3doc}
\begin{document}
\DocInput{l3quark.dtx}
\end{document}
%</driver>
% \fi
%
%
% \title{The \textsf{l3quark} package\thanks{This file
%         has version number \fileversion, last
%         revised \filedate.}\\
% ``Quarks''}
% \author{\Team}
% \date{\filedate}
% \maketitle
%
% \begin{documentation}
%
% A special type of constants in \LaTeX3 are `quarks'. These are control
% sequences that expand to themselves and should therefore NEVER be
% executed directly in the code. This would result in an endless loop!
%
% They are meant to be used as delimiter is weird functions (for
% example as the stop token (i.e., "\q_stop"). They also permit the
% following ingenious trick: when you pick up a token in a temporary,
% and you want to know whether you have picked up a particular quark,
% all you have to do is compare the temporary to the quark using
% "\if_meaning:w". A set of special quark testing functions is set up
% below. All the quark testing functions are expandable although the
% ones testing only single tokens are much faster.
%
% By convention all constants of type quark start out with "\q_".
%
% The documentation needs some updating.
%
% \section{Functions}
%
% \begin{function}{ \quark_new:N }
% \begin{syntax}
%    "\quark_new:N" <quark>
% \end{syntax}
% Defines <quark> to be a new constant of type "quark".
% \end{function}
%
% \begin{function}{%
%                  \quark_if_no_value:n   / (pTF) ,
%                  \quark_if_no_value:N   / (pTF) ,
% }
% \begin{syntax}
%    "\quark_if_no_value:nTF" \Arg{token list} \Arg{true code} \Arg{false code}
%    "\quark_if_no_value:NTF" <tl var.> \Arg{true code} \Arg{false code}
% \end{syntax}
% This tests whether or not <token list> contains only the quark
% "\q_no_value".
%
% If <token list> to be tested is stored in a token list variable use
% "\quark_if_no_value:NTF", or "\quark_if_no_value:NF" or check the
% value directly with "\if_meaning:w". All those cases are faster then
% "\quark_if_no_value:nTF" so should be preferred.\footnote{Clarify
% semantic of the ``n'' case \ldots{} i think it is not implement
% according to what we originally intended /FMi}
%
% \begin{texnote}
% But  be aware of the fact that "\if_meaning:w" can result in an
% overflow of \TeX{}'s parameter stack since it leaves the corresponding
% "\fi:" on the input until the whole replacement text is processed. It
% is therefore better in recursions to use "\quark_if_no_value:NTF" as
% it will remove the conditional prior to processing the "T" or "F" case
% and so allows tail-recursion.
% \end{texnote}
% \end{function}
%
% \begin{function}{%
%                  \quark_if_nil:N   / (pTF) ,
% }
% \begin{syntax}
%    "\quark_if_nil:NTF" <token> \Arg{true code} \Arg{false code}
% \end{syntax}
% This tests whether or not <token> is equal to the quark
% "\q_nil".
%
% This is a useful test for recursive loops which typically has 
% "\q_nil" as an end marker.
% \end{function}
%
%
% \begin{function}{%
%                  \quark_if_nil:n   / (pTF) ,
%                  \quark_if_nil:V   / (pTF) ,
%                  \quark_if_nil:o   / (pTF) ,
% }
% \begin{syntax}
%    "\quark_if_nil:nTF" \Arg{tokens} \Arg{true code} \Arg{false code}
% \end{syntax}
% This tests whether or not <tokens> is equal to the quark
% "\q_nil".
%
% This is a useful test for recursive loops which typically has
% "\q_nil" as an end marker.
% \end{function}
%
% \section{Recursion}
%
% This module provides a uniform interface to intercepting and
% terminating loops as when one is doing tail recursion. The building
% blocks follow below.
% 
% \begin{variable}{\q_recursion_tail}
%   This quark is appended to the data structure in question and
%   appears as a real element there. This means it gets any list
%   separators around it.
% \end{variable}
%
% \begin{variable}{\q_recursion_stop} 
%   This quark is added \emph{after} the data structure. Its purpose
%   is to make it possible to terminate the recursion at any point
%   easily.
% \end{variable}
% 
% \begin{function}{%
%                  \quark_if_recursion_tail_stop:N / (EXP) ,
%                  \quark_if_recursion_tail_stop:n / (EXP) ,
%                  \quark_if_recursion_tail_stop:o / (EXP) ,
% }
% \begin{syntax}
%    "\quark_if_recursion_tail_stop:n" \Arg{list element} \\
%    "\quark_if_recursion_tail_stop:N" <list element>
% \end{syntax}
% This tests whether or not <list element> is equal to
% "\q_recursion_tail" and then exits, i.e., it gobbles the remainder of
% the list up to and including "\q_recursion_stop" which \emph{must}
% be present.
%
% If <list element> is not under your complete control it is advisable
% to use the "n". If you wish to use the "N" form you \emph{must}
% ensure it is really a single token such as if you have
% \begin{quote}
% "\tl_set:Nn \l_tmpa_tl {" <list element> "}"
% \end{quote}
% \end{function}
%
% \begin{function}{%
%                  \quark_if_recursion_tail_stop_do:Nn / (EXP) ,
%                  \quark_if_recursion_tail_stop_do:nn / (EXP) ,
%                  \quark_if_recursion_tail_stop_do:on / (EXP) ,
% }
% \begin{syntax}
%   "\quark_if_recursion_tail_stop_do:nn"
%   ~~~~\Arg{list element} \Arg{post action} 
%   "\quark_if_recursion_tail_stop_do:Nn"
%   ~~~~<list element> \Arg{post action}
% \end{syntax}
% Same as "\quark_if_recursion_tail_stop:N" except here the second
% argument is executed after the recursion has been terminated.
% \end{function}
%
% \section{Constants}
%
% \begin{variable}{\q_no_value} The canonical `missing value quark'
% that is returned by certain functions to denote that a requested value
% is not found in the data structure.
% \end{variable}
%
% \begin{variable}{\q_stop}
% This constant is used as a a marker in parameter text. This allows a
% scanning function to find the end of some input string.
% \end{variable}
%
% \begin{variable}{\q_nil}
% This constant represent the nil pointer in pointer structures.
% \end{variable}
%
% \begin{variable}{\q_error} 
%    Delimits the end of
%    the computation for purposes of error recovery.
% \end{variable}
%
% \begin{variable}{\q_mark} 
%    Used in parameter text when we need a scanning boundary that is
%    distinct from |\q_stop|.
% \end{variable}
%
% \end{documentation}
%
% \begin{implementation}
%
% \section{\pkg{l3quark} implementation}
%
% \TestFiles{m3quark001.lvt}
%
%    We start by ensuring that the required packages are loaded.
%    We check for \texttt{l3expan} since this a basic package that is
%    essential for use of any higher-level package.
%    \begin{macrocode}
%<*package>
\ProvidesExplPackage
  {\filename}{\filedate}{\fileversion}{\filedescription}
\package_check_loaded_expl:
%</package>
%<*initex|package>
%    \end{macrocode}
%
% \begin{macro}{\quark_new:N}
%    Allocate a new quark.
% \UnitTested
%    \begin{macrocode}
\cs_new_protected_nopar:Npn \quark_new:N #1 { \tl_const:Nn #1 {#1} }
%    \end{macrocode}
% \end{macro}
%
% \begin{variable}{\q_stop,\q_no_value,\q_nil}
%    |\q_stop| is often used as a marker in parameter text,
%    |\q_no_value| is the canonical missing value, and |\q_nil|
%    represents a nil pointer in some data structures.
%    \begin{macrocode}
\quark_new:N \q_stop
\quark_new:N \q_no_value
\quark_new:N \q_nil
%    \end{macrocode}
% \end{variable}
%
% \begin{variable}{\q_error,\q_mark}
%    We need two additional quarks.  |\q_error| delimits the end of
%    the computation for purposes of error recovery.  |\q_mark| is
%    used in parameter text when we need a scanning boundary that is
%    distinct from |\q_stop|.
%    \begin{macrocode}
\quark_new:N\q_error
\quark_new:N\q_mark
%    \end{macrocode}
% \end{variable}
%
%
% \begin{variable}{\q_recursion_tail,\q_recursion_stop}
%   Quarks for ending recursions. Only ever used there!
%   |\q_recursion_tail| is appended to whatever list structure we are
%   doing recursion on, meaning it is added as a proper list item with
%   whatever list separator is in use.  |\q_recursion_stop| is placed
%   directly after the list.
%    \begin{macrocode}
\quark_new:N\q_recursion_tail
\quark_new:N\q_recursion_stop
%    \end{macrocode}
% \end{variable}
%
% \begin{macro}{\quark_if_recursion_tail_stop:n,
%               \quark_if_recursion_tail_stop:N,
%               \quark_if_recursion_tail_stop:o}
% \UnitTested
%   When doing recursions it is easy to spend a lot of time testing if
%   we found the end marker. To avoid this, we use a recursion end
%   marker every time we do this kind of task. Also, if the recursion
%   end marker is found, we wrap things up and finish.
%    \begin{macrocode}
\cs_new:Npn \quark_if_recursion_tail_stop:n #1 {
  \exp_after:wN\if_meaning:w
    \quark_if_recursion_tail_aux:w #1?\q_stop\q_recursion_tail\q_recursion_tail
    \exp_after:wN \use_none_delimit_by_q_recursion_stop:w
  \fi:
}
\cs_new:Npn \quark_if_recursion_tail_stop:N #1 {
  \if_meaning:w#1\q_recursion_tail
    \exp_after:wN \use_none_delimit_by_q_recursion_stop:w
  \fi:
}
\cs_generate_variant:Nn \quark_if_recursion_tail_stop:n {o}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\quark_if_recursion_tail_stop_do:nn,
%               \quark_if_recursion_tail_stop_do:Nn,
%               \quark_if_recursion_tail_stop_do:on}
% \UnitTested
% These functions are variants of the above that
% inserts tokens into the input stream after a
% recursion process is finalised.
%    \begin{macrocode}
\cs_new:Npn \quark_if_recursion_tail_stop_do:nn #1#2 {
  \exp_after:wN\if_meaning:w
    \quark_if_recursion_tail_aux:w #1?\q_stop\q_recursion_tail\q_recursion_tail
    \exp_after:wN \use_i_delimit_by_q_recursion_stop:nw
  \else:
    \exp_after:wN\use_none:n
  \fi:
  {#2}
}
\cs_new:Npn \quark_if_recursion_tail_stop_do:Nn #1#2 {
  \if_meaning:w #1\q_recursion_tail
    \exp_after:wN \use_i_delimit_by_q_recursion_stop:nw
  \else:
    \exp_after:wN\use_none:n
  \fi:
  {#2}
}
\cs_generate_variant:Nn \quark_if_recursion_tail_stop_do:nn {on}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}[aux]{\quark_if_recursion_tail_aux:w}
%    \begin{macrocode}
\cs_new:Npn \quark_if_recursion_tail_aux:w #1#2 \q_stop \q_recursion_tail {#1}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}[pTF]{\quark_if_no_value:N,\quark_if_no_value:n}
% \UnitTested
%    Here we test if we found a special quark as the first argument.
%    We better start with |\q_no_value| as the first argument since
%    the whole thing may otherwise loop if |#1| is wrongly given
%    a string like |aabc| instead of a single token.\footnote{It may
%    still loop in special circumstances however!}
%    \begin{macrocode}
\prg_new_conditional:Nnn \quark_if_no_value:N {p,TF,T,F} {
  \if_meaning:w \q_no_value #1
    \prg_return_true: \else: \prg_return_false: \fi:
}
%    \end{macrocode}
% These tests are easy with \cs{pdf_strcmp:D} available.
%    \begin{macrocode}
\prg_new_conditional:Nnn \quark_if_no_value:n {p,TF,T,F} {
  \if_num:w \pdf_strcmp:D
      {\exp_not:N \q_no_value}
      {\exp_not:n{#1}} = \c_zero
    \prg_return_true: \else: \prg_return_false:
  \fi:
}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}[pTF]{\quark_if_nil:N}
% \UnitTested
%    A function to check for the presence of |\q_nil|.
%    \begin{macrocode}
\prg_new_conditional:Nnn \quark_if_nil:N {p,TF,T,F} {
  \if_meaning:w \q_nil #1 \prg_return_true: \else: \prg_return_false: \fi:
}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}[pTF]{\quark_if_nil:n,\quark_if_nil:V,\quark_if_nil:o}
% \UnitTested
%    A function to check for the presence of |\q_nil|.
%    \begin{macrocode}
\prg_new_conditional:Nnn \quark_if_nil:n {p,TF,T,F} {
  \if_num:w \pdf_strcmp:D
      {\exp_not:N \q_nil}
      {\exp_not:n{#1}} = \c_zero
    \prg_return_true: \else: \prg_return_false:
  \fi:
}
\cs_generate_variant:Nn \quark_if_nil_p:n {V}
\cs_generate_variant:Nn \quark_if_nil:nTF {V}
\cs_generate_variant:Nn \quark_if_nil:nT  {V}
\cs_generate_variant:Nn \quark_if_nil:nF  {V}
\cs_generate_variant:Nn \quark_if_nil_p:n {o}
\cs_generate_variant:Nn \quark_if_nil:nTF {o}
\cs_generate_variant:Nn \quark_if_nil:nT  {o}
\cs_generate_variant:Nn \quark_if_nil:nF  {o}
%    \end{macrocode}
% \end{macro}
%
%
%
%    Show token usage:
%    \begin{macrocode}
%<*showmemory>
\showMemUsage
%</showmemory>
%    \end{macrocode}
%
% \end{implementation}
% \PrintIndex
%
% \endinput
