%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%                                                         %%
%%  GuTable 1.04 (October 12, 2025)                        %%
%%                                                         %%
%%  A table mashinery compatible with LaTeX and Plain TeX  %%
%%  Just insert "\input gutable" in your TeX file          %%
%%                                                         %%
%%  (c) Alexander E. Gutman <gutman@math.nsc.ru>           %%
%%                                                         %%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
%%  Version History
%%
%%  1.00 (September 28, 2020)
%%  The initial version
%%
%%  1.01 (September 8, 2021)
%%  Dots in captions are typeset in the same font as the preceding text. (See \defcap@.)
%%
%%  1.02 (April 23, 2022)
%%  "\hbox to\hsize" is used instead of "\line"
%%
%%  1.03 (April 24, 2022)
%%  The \cell command is added as a synonym for & in tables.
%%  (In particular, this is useful for Beamer, where & produces an error.)
%%
%%  1.04 (October 12, 2025)
%%  Removed the action of the character with ASCII code 7 in the code environment.
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

{\def\yes{yes}\expandafter\ifx\csname gutable.tex loaded\endcsname\yes\endinput\fi}
\expandafter\def\csname gutable.tex loaded\endcsname{yes}

\expandafter\edef\csname restore at\endcsname{\catcode`\noexpand\@\the\catcode`\@\relax}
\catcode`\@=11\relax

% \def\normalsize {...} % Define your "normal" size command here
% \def\small      {...} % Define your "small" size command here
% \def\smallcaps  {...} % Define your "small caps" font command here
% \def\sl         {...} % Define your "slanted" font command here

% Replace missing sizes and fonts
\ifx\normalsize\undefined
  \ifx\xipoint\undefined\ifx\xpoint\undefined\ifx\tenpoint\undefined\let\normalsize=\relax\else\def\normalsize{\tenpoint}\fi\else\def\normalsize{\xpoint}\fi\else\def\normalsize{\xipoint}\fi
\fi
\ifx\small\undefined
  \ifx\ixpoint\undefined\ifx\ninepoint\undefined\let\small=\relax\else\def\small{\ninepoint}\fi\else\def\small{\ixpoint}\fi
\fi
\ifx\smallcaps\undefined
  \ifx\smc\undefined\ifx\sc\undefined\let\smallcaps=\relax\else\def\smallcaps{\sc}\fi\else\def\smallcaps{\smc}\fi
\fi
\ifx\sl\undefined\def\sl{\it}\fi

\def\sp@ce{ }

% Step
\def\if@step#1#2#3{% If \step@ = #1 then do #2 else do #3
  \edef\step@@{Step:#1}\ifx\step@\step@@#2\else#3\fi
}
\def\def@step#1{\xdef\step@{Step:#1}}
\def@step{undefined}

% Debugging
\newif\if@debug\@debugtrue
\def\debug@#1{\if@debug\message{^^J\step@\sp@ce row:\the\row@\sp@ce col:\the\col@\sp@ce\string{ #1 \string}^^J}\fi\ignorespaces}
\def\debug@p#1{\debug@{#1}\show\relax\ignorespaces}

% If the next token = #1 then do #2 else do #3
\long\def\if@nexttoken#1#2#3{\let\@d@=#1\def\@a@{#2}\def\@b@{#3}\futurelet\next@token\if@nexttoken@}
\def\space@.{\futurelet\space@\relax}\space@. % \space@ := blank space
\def\if@nexttoken@{%
  \ifx\next@token\space@   \let\@c@=\if@nexttoken@@
  \else\ifx\next@token\@d@ \let\@c@=\@a@
  \else                    \let\@c@=\@b@
  \fi\fi
  \@c@
}
% \if@nexttoken@@ := Eat spaces, determine \next@token, and call \if@nexttoken@
\begingroup\def\:{\if@nexttoken@@}\expandafter\gdef\: {\futurelet\next@token\if@nexttoken@}\endgroup

% Dry run
\long\def\run@#1{\setbox\z@\hbox{#1}}

% Alignment environment for caption and body
\def\caption@leftskip{\z@ plus 1 fil}\def\caption@rightskip{\z@ plus 1 fil}
\long\def\align@caption#1{%
  \par
  \begingroup
    \leftskip=\caption@leftskip\relax\rightskip=\caption@rightskip\relax
    \parindent\z@\parfillskip\z@
    \def\\{\unskip\nopagebreak\par\ignorespaces}%
    #1\par
  \endgroup
}
\def\body@leftskip{\z@ plus 1 fil}\def\body@rightskip{\z@ plus 1 fil}
\long\def\align@body#1{\hbox to\hsize{\hskip\body@leftskip\relax#1\hskip\body@rightskip\relax}}

% New registers
\newcount\count@@ % \count@ is also available
\newcount\col@count
\newcount\top@count
\newcount\row@count
\newcount\row@
\newcount\col@
\newdimen\dimen@@ % \dimen@ is also available
\newdimen\dimen@@@
\newtoks\align@content
\newtoks\figtab@body

\def\min@length{.00002pt} % The smallest length in TeX

% Figure and table "frills" (name, heading, caption, body, ...)

\def\def@figtab@frills{%
  \def@figtab@frills@
  \def\name@{}\def\heading@{}\def\caption@{}\figtab@body{}%
  \def\before@{\bigskip}\def\after@{\bigskip\noindent}%
  \def\topcap@{\defcap@\ifx\cap@\empty\else\align@caption{\cap@}\nopagebreak\medskip\fi}%
  \def\botcap@{\defcap@\ifx\cap@\empty\else\nopagebreak\medskip\align@caption{\cap@}\fi}%
  \let\add@postbreak=\relax
  \let\custom@body=\relax
  \long\def\before##1{\def\before@{##1}\ignorespaces}\long\def\after##1{\def\after@{##1}\ignorespaces}%
  \def\captionleftskip##1{\def\caption@leftskip{##1}}\def\captionrightskip##1{\def\caption@rightskip{##1}}%
  \def\bodyleftskip##1{\def\body@leftskip{##1}}\def\bodyrightskip##1{\def\body@rightskip{##1}}%
  \long\def\body##1\endbody{\let\custom@body=1\figtab@body{##1}\ignorespaces}%
  \def\usetopcaption{\def\inserttopcap@{\topcap@\global\let\add@postbreak=1}\def\insertbotcap@{}}%
  \def\usebotcaption{\def\inserttopcap@{}\def\insertbotcap@{\botcap@\global\let\add@postbreak=1}}%
  \def\captionsize##1{\def\captionsize@{##1}\ignorespaces}%
  \def\namefont##1{\def\namefont@{##1}\ignorespaces}%
  \def\headingfont##1{\def\headingfont@{##1}\ignorespaces}%
  \def\captionfont##1{\def\captionfont@{##1}\ignorespaces}%
  \usetopcaption\captionsize{\small}\namefont{\bf}\headingfont{\smallcaps}\captionfont{\rm}%
  \captionleftskip{\z@ plus 1 fil}\captionrightskip{\z@ plus 1 fil}%
  \bodyleftskip{\z@ plus 1 fil}\bodyrightskip{\z@ plus 1 fil}%
}

\def\def@figtab@frills@{%
  \def\name##1{\def\name@{##1}\ignorespaces}%
  \def\heading##1{\def\heading@{##1}\ignorespaces}%
  \long\def\caption##1{\def\caption@{##1}\ignorespaces}%
}%

\def\def@table@frills{%
  \def@figtab@frills
  \def\breakfont##1{\def\breakfont@{##1}\ignorespaces}%
  \def\footer@{}\def\footersize@{}%
  \def\footersize##1{\def\footersize@{##1}\ignorespaces}%
  \def\footerfont##1{\def\footerfont@{##1}\ignorespaces}%
  \long\def\footer##1{\def\footer@{##1}\ignorespaces}%
  \def\float{%
    \ifx\midinsert\undefined
      \errmessage{\string\float\sp@ce is supported only in Plain TeX and its extensions}%
    \else
      \def\before@{\midinsert}\def\after@{\endinsert}\def\interbreak@{\endinsert\midinsert}%
      \def\float@message####1{\errmessage{\string\before, \string\after, and \string\interbreak\sp@ce are not allowed for \string\float}}%
      \let\before=\float@message \let\after=\float@message \let\interbreak=\float@message
    \fi
  }%
  \let\table@inline=\relax
  \def\inline{\let\table@inline=1}%
  \def\usebotcaption{\errmessage{\string\usebotcaption\sp@ce is allowed for \string\Figure\sp@ce but not for \string\Table}}%
  \def\prebreak@{}\def\interbreak@{}\def\postbreak@{}\let\add@postbreak=\relax
  \def@table@frills@
  \prebreaktext{continued on the next page}\interbreak{\newpage}\postbreaktext{continued}%
  \def\interbreaksize@{}%
  \def\interbreaksize##1{\def\interbreaksize@{##1}\ignorespaces}%
  \breakfont{\sl}\interbreaksize{\normalsize}\footersize{\small}\footerfont{\rm}%
}
\def\def@table@frills@{%
  \long\def\prebreak##1{\def\prebreak@{##1}\ignorespaces}%
  \long\def\prebreaktext##1{\def\prebreaktext@{##1}\prebreak{({\breakfont@\prebreaktext@\/})}\ignorespaces}%
  \long\def\interbreak##1{\def\interbreak@{{\normalsize##1}}\ignorespaces}%
  \long\def\postbreak##1{\def\postbreak@{##1}\ignorespaces}%
  \long\def\postbreaktext##1{\def\postbreaktext@{##1}\postbreak{({\breakfont@\postbreaktext@\/})}\ignorespaces}%
}

\def\def@figure@frills{%
  \def@figtab@frills
  \def\float{%
    \ifx\midinsert\undefined
      \errmessage{\string\float\sp@ce is supported only in Plain TeX and its extensions}%
    \else
      \def\before@{\midinsert}\def\after@{\endinsert}%
    \fi
  }%
}

\def\defcap@{%
  \ifx\name@\empty\let\name@@=\empty\else\def\name@@{{\namefont@\name@}}\fi
  \ifx\heading@\empty\let\heading@@=\empty\else\def\heading@@{{\headingfont@\heading@}}\fi
  \let\precaption@point=.%
  \ifx\add@postbreak1%
    \ifx\caption@\empty
      \ifx\postbreak@\empty
        \let\caption@@=\empty
      \else
        \def\caption@@{{\postbreak@}}%
        \let\precaption@point=\relax
      \fi
    \else
      \ifx\postbreak@\empty
        \def\caption@@{{\captionfont@\caption@}}%
      \else
        \def\caption@@{{\captionfont@\caption@} {\postbreak@}}%
      \fi
    \fi
  \else
    \ifx\caption@\empty\let\caption@@=\empty\else\def\caption@@{{\captionfont@\caption@}}\fi
  \fi
  \ifx\name@@\empty\ifx\heading@@\empty\ifx\caption@@\empty
    \let\cap@=\empty
  \else
    \def\cap@{\captionsize@\caption@@}%
  \fi\else\ifx\caption@@\empty
    \def\cap@{\captionsize@\heading@@}%
  \else
    \def\cap@{\captionsize@\heading@@{\headingfont@\precaption@point} \caption@@}%
  \fi\fi\else\ifx\heading@@\empty\ifx\caption@@\empty
    \def\cap@{\captionsize@\name@@}%
  \else
    \def\cap@{\captionsize@\name@@{\namefont@\precaption@point} \caption@@}%
  \fi\else\ifx\caption@@\empty
    \def\cap@{\captionsize@\name@@{\namefont@.} \heading@@}%
  \else
    \def\cap@{\captionsize@\name@@{\namefont@.} \heading@@{\headingfont@\precaption@point} \caption@@}%
  \fi\fi\fi
}

% "Object-oriented" syntax related to table, columns, rows, and cells

% Get

\def\get@#1->#2{\expandafter\let\expandafter#2\csname#1\endcsname}
\def\get@@col[#1]{\get@ col[\the#1]} \def\get@@row[#1]{\get@ row[\the#1]} \def\get@@cell[#1,#2]{\get@ cell[\the#1,\the#2]}
\def\get@col{\get@@col[\col@]} \def\get@row{\get@@row[\row@]} \def\get@cell{\get@@cell[\row@,\col@]}
\def\get@table{\get@ table}

% Let

\def\let@#1=#2{\expandafter\let\csname#1\endcsname#2}
\def\let@@col[#1]{\let@ col[\the#1]} \def\let@@row[#1]{\let@ row[\the#1]} \def\let@@cell[#1,#2]{\let@ cell[\the#1,\the#2]}
\def\let@col{\let@@col[\col@]} \def\let@row{\let@@row[\row@]} \def\let@cell{\let@@cell[\row@,\col@]}
\def\let@table{\let@ table}

% Def

\def\def@#1=#2{\def\lastdef@value{#2}\let@#1=\lastdef@value}
\def\gdef@#1=#2{\def\lastdef@value{#2}\global\let@#1=\lastdef@value}
\def\edef@#1=#2{\edef\lastdef@value{#2}\let@#1=\lastdef@value}
\def\xdef@#1=#2{\edef\lastdef@value{#2}\global\let@#1=\lastdef@value}

\def\def@@col[#1]{\def@ col[\the#1]}             \def\gdef@@col[#1]{\gdef@ col[\the#1]}             \def\edef@@col[#1]{\edef@ col[\the#1]}             \def\xdef@@col[#1]{\xdef@ col[\the#1]}
\def\def@@row[#1]{\def@ row[\the#1]}             \def\gdef@@row[#1]{\gdef@ row[\the#1]}             \def\edef@@row[#1]{\edef@ row[\the#1]}             \def\xdef@@row[#1]{\xdef@ row[\the#1]}
\def\def@@cell[#1,#2]{\def@ cell[\the#1,\the#2]} \def\gdef@@cell[#1,#2]{\gdef@ cell[\the#1,\the#2]} \def\edef@@cell[#1,#2]{\edef@ cell[\the#1,\the#2]} \def\xdef@@cell[#1,#2]{\xdef@ cell[\the#1,\the#2]}

\def\def@col{\def@@col[\col@]}         \def\gdef@col{\gdef@@col[\col@]}         \def\edef@col{\edef@@col[\col@]}         \def\xdef@col{\xdef@@col[\col@]}
\def\def@row{\def@@row[\row@]}         \def\gdef@row{\gdef@@row[\row@]}         \def\edef@row{\edef@@row[\row@]}         \def\xdef@row{\xdef@@row[\row@]}
\def\def@cell{\def@@cell[\row@,\col@]} \def\gdef@cell{\gdef@@cell[\row@,\col@]} \def\edef@cell{\edef@@cell[\row@,\col@]} \def\xdef@cell{\xdef@@cell[\row@,\col@]}

\def\def@table{\def@ table} \def\gdef@table{\gdef@ table} \def\edef@table{\edef@ table} \def\xdef@table{\xdef@ table}

% Val

\def\val@#1 {\csname#1\endcsname}
\def\val@@col[#1]{\val@ col[\the#1]} \def\val@@row[#1]{\val@ row[\the#1]} \def\val@@cell[#1,#2]{\val@ cell[\the#1,\the#2]}
\def\val@col{\val@@col[\col@]} \def\val@row{\val@@row[\row@]} \def\val@cell{\val@@cell[\row@,\col@]}
\def\val@table{\val@ table}

% If

\def\if@#1=#2#3#4{\get@#1->\lastif@value\ifx\lastif@value#2#3\else#4\fi}
\def\if@@col[#1]{\if@ col[\the#1]} \def\if@@row[#1]{\if@ row[\the#1]} \def\if@@cell[#1,#2]{\if@ cell[\the#1,\the#2]}
\def\if@col{\if@@col[\col@]} \def\if@row{\if@@row[\row@]} \def\if@cell{\if@@cell[\row@,\col@]}
\def\if@table{\if@ table}

% Other methods

\def\put@#1=#2{#1=#2\relax             \if@nexttoken+{\advance@p#1}{\if@nexttoken-{\advance@m#1}{}}}
\def\advance@p#1+#2{\advance#1#2\relax \if@nexttoken+{\advance@p#1}{\if@nexttoken-{\advance@m#1}{}}}
\def\advance@m#1-#2{\advance#1-#2\relax\if@nexttoken+{\advance@p#1}{\if@nexttoken-{\advance@m#1}{}}}

\def\get@row@of#1->#2{#2\expandafter\row@of@#1\relax}\def\row@of@[#1,#2]{#1}
\def\get@col@of#1->#2{#2\expandafter\col@of@#1\relax}\def\col@of@[#1,#2]{#2}

\long\def\foreach@row#1{\def\break@foreach@row{\row@=\row@count}\row@0\relax\long\def\row@body{#1}\row@iterate}\def\row@iterate{\advance\row@1\relax\row@body\ifnum\row@<\row@count\let\row@next=\row@iterate\else\let\row@next=\relax\fi\row@next}
\long\def\foreach@Row#1{\def\break@foreach@Row{\row@=\row@count}\row@0\relax\long\def\Row@body{#1}\Row@iterate}\def\Row@iterate{\advance\row@1\relax\Row@body\ifnum\row@<\row@count\let\Row@next=\Row@iterate\else\let\Row@next=\relax\fi\Row@next}
\long\def\foreach@col#1{\def\break@foreach@col{\col@=\col@count}\col@0\relax\long\def\col@body{#1}\col@iterate}\def\col@iterate{\advance\col@1\relax\col@body\ifnum\col@<\col@count\let\col@next=\col@iterate\else\let\col@next=\relax\fi\col@next}
\long\def\foreach@Col#1{\def\break@foreach@Col{\col@=\col@count}\col@0\relax\long\def\Col@body{#1}\Col@iterate}\def\Col@iterate{\advance\col@1\relax\Col@body\ifnum\col@<\col@count\let\Col@next=\Col@iterate\else\let\Col@next=\relax\fi\Col@next}

\def\let@parent[#1,#2]=#3{%
  % Let cell[#1,#2].parent := #3, update parent.rowspanto/colspanto,
  % and recursively call let@parent for the neighboring cells affected according to rowspanto/colspanto
  \begingroup
    \edef\r@{\the#1}%
    \edef\c@{\the#2}%
    \edef\cell@{cell[\r@,\c@]}%
    \let\parent@=#3\relax
    % \cell@.parent := \parent@
    \global\let@\cell@.parent=\parent@
    % \parent@.rowspanto := max { \parent@.rowspanto, \cell@.rowspanto, #1 }
    \get@\parent@.rowspanto->\rowspanto@
    \ifx\rowspanto@\relax\def\rowspanto@{0}\fi
    \get@\cell@.rowspanto->\cellrowspanto@
    \ifx\cellrowspanto@\relax\let\cellrowspanto@=\r@\fi
    \ifnum\rowspanto@<\cellrowspanto@\relax
      \let\rowspanto@=\cellrowspanto@
      \global\let@\parent@.rowspanto=\rowspanto@
    \fi
    % \parent@.colspanto := max { \parent@.colspanto, \cell@.colspanto, #2 }
    \get@\parent@.colspanto->\colspanto@
    \ifx\colspanto@\relax\def\colspanto@{0}\fi
    \get@\cell@.colspanto->\cellcolspanto@
    \ifx\cellcolspanto@\relax\let\cellcolspanto@=\c@\fi
    \ifnum\colspanto@<\cellcolspanto@\relax
      \let\colspanto@=\cellcolspanto@
      \global\let@\parent@.colspanto=\colspanto@
    \fi
    \ifnum\rowspanto@>\r@\relax
      % Recursively call let@parent[#1+1,#2]=\parent@
      \put@\count@=\r@+1%
      \put@\count@@=\c@
      \let@parent[\count@,\count@@]=\parent@
    \fi
    \ifnum\colspanto@>\c@\relax
      % Recursively call let@parent[#1,#2+1]=\parent@
      \put@\count@=\r@
      \put@\count@@=\c@+1%
      \let@parent[\count@,\count@@]=\parent@
    \fi
  \endgroup
}

\def\bad@cell#1{\errmessage{Cell \the\col@\sp@ce in row \the\row@\sp@ce#1}}
\def\cell@name cell[#1,#2]{cell #2 in row #1}

% Options machinery

\def\context@table{table}\def\context@col{col}\def\context@row{row}\def\context@cell{cell}

\def\let@context.#1=#2{\csname let@\context@\endcsname.#1=#2}
\def\if@context{\csname if@\context@\endcsname}

\def\opt@u{_}\def\opt@up{_+}\def\opt@um{_-}
\def\opt@v{|}\def\opt@vp{|+}\def\opt@vm{|-}
\def\opt@C{CW}\def\opt@Cp{CW+}\def\opt@Cm{CW-}
\def\opt@l{<}\def\opt@c{^}
\def\opt@F{F}\def\opt@A{A}\def\opt@VA{VA}\def\opt@W{W}\def\opt@H{H}\def\opt@D{D}\def\opt@M{M}\def\opt@SV{SV}\def\opt@SH{SH}
\def\opt@T{T}\def\opt@B{B}\def\opt@TB{TB}\def\opt@Tx{Tx}\def\opt@Bx{Bx}\def\opt@TBx{TBx}
\def\opt@L{L}\def\opt@R{R}\def\opt@LR{LR}\def\opt@Lx{Lx}\def\opt@Rx{Rx}\def\opt@LRx{LRx}

\def\value@L{L}   \def\value@C{C}   \def\value@R{R}
\def\value@LL{LL} \def\value@CL{CL} \def\value@RL{RL}
\def\value@LC{LC} \def\value@CC{CC} \def\value@RC{RC}
\def\value@LR{LR} \def\value@CR{CR} \def\value@RR{RR}
\def\value@xL{*L} \def\value@xC{*C} \def\value@xR{*R}
\def\value@T{T}   \def\value@M{M}   \def\value@B{B}

\def\value@plus{+}\def\value@minus{-}\def\value@Q{?}\def\value@zero{0}

\def\parse@option#1:#2:{\gdef\opt@{#1}\gdef\value@{#2}}

\def\process@framevalues#1{%
  \let\temp@#1%
  \let\next@=\process@framevalues
  \ifx\temp@\relax\let\next@=\relax\else
  \ifx\temp@ T\let@table.frametop=1\else
  \ifx\temp@ B\let@table.framebottom=1\else
  \ifx\temp@ L\let@table.frameleft=1\else
  \ifx\temp@ R\let@table.frameright=1\else
    \errmessage{Option [F] has subvalue "#1", while only "T", "B", "L", or "R" are allowed}%
  \fi\fi\fi\fi\fi
  \next@
}

\def\process@option#1{%
  \edef\value@{#1}%
  \expandafter\run@\expandafter{\expandafter\parse@option\value@::}%
  \ifx\opt@\opt@F % [F:T/B/L/R/TB/.../TBLR]
    \ifx\context@\context@table\else\errmessage{Option [F:...] is allowed only for \string\Table}\fi
    \let@table.frametop=0\let@table.framebottom=0\let@table.frameleft=0\let@table.frameright=0%
    \expandafter\process@framevalues\value@\relax
  \else\ifx\opt@\opt@l % [<]
    \ifx\context@\context@cell\else\errmessage{Option [\string<] is allowed only for cells in rows}\fi
    \ifx\value@\empty\else\errmessage{Option [\string<] does not assume a value}\fi
    \if@cell.spanned=1{\bad@cell{is spanned several times}}{}%
    \ifnum\col@=1\relax\bad@cell{may not contain [\string<] (it is in the first column)}\fi
    % \parent@ := cell[\row@,\col@-1] or its parent if the latter is defined
    \put@\count@=\col@-1%
    \get@@cell[\row@,\count@].parent->\parent@
    \ifx\parent@\relax\edef\parent@{cell[\the\row@,\the\count@]}\fi
    % cell[\row@,\col@].parent := \parent@
    \let@parent[\row@,\col@]=\parent@
    \let@cell.spanned=1%
  \else\ifx\opt@\opt@c % [^]
    \ifx\context@\context@cell\else\errmessage{Option [\string^] is allowed only for cells in rows}\fi
    \ifx\value@\empty\else\errmessage{Option [\string^] does not assume a value}\fi
    \if@cell.spanned=1{\bad@cell{is spanned several times}}{}%
    \ifnum\row@=1\relax\bad@cell{may not contain [\string^] (it is in the first row)}\fi
    \put@\count@=\top@count+1%
    \ifnum\row@=\count@\bad@cell{may not contain [\string^] (it is under the last top row)}\fi
    \ifnum\row@=\bot@start\relax\bad@cell{may not contain [\string^] (it is in the first bottom row)}\fi
    % \parent@ := cell[\row@-1,\col@] or its parent if the latter is defined
    \put@\count@=\row@-1%
    \get@@cell[\count@,\col@].parent->\parent@
    \ifx\parent@\relax\edef\parent@{cell[\the\count@,\the\col@]}\fi
    % cell[\row@,\col@].parent := \parent@
    \let@parent[\row@,\col@]=\parent@
    \let@row.spanned=1%
    \let@cell.spanned=1%
  \else\ifx\opt@\opt@u % [_:+], [_:-], [_] := [_:+]
    \let\value@@=\relax
    \ifx\value@\empty\let\value@@=1\fi\ifx\value@\value@plus\let\value@@=1\fi\ifx\value@\value@minus\let\value@@=0\fi
    \ifx\value@@\relax\errmessage{Option [\string_:...] admits only values + or -}\fi
    \let@context.rowsep=\value@@
  \else\ifx\opt@\opt@up % [_+] := [_:+]
    \ifx\value@\empty\else\errmessage{Option [\string_+] does not assume a value}\fi
    \let@context.rowsep=1%
  \else\ifx\opt@\opt@um % [_-] := [_:-]
    \ifx\value@\empty\else\errmessage{Option [\string_-] does not assume a value}\fi
    \let@context.rowsep=0%
  \else\ifx\opt@\opt@v % [|:+], [|:-], [|] := [|:+]
    \let\value@@=\relax
    \ifx\value@\empty\let\value@@=1\fi\ifx\value@\value@plus\let\value@@=1\fi\ifx\value@\value@minus\let\value@@=0\fi
    \ifx\value@@\relax\errmessage{Option [\string|:...] admits only values + or -}\fi
    \let@context.colsep=\value@@
  \else\ifx\opt@\opt@vp % [|+] := [|:+]
    \ifx\value@\empty\else\errmessage{Option [\string|+] does not assume a value}\fi
    \let@context.colsep=1%
  \else\ifx\opt@\opt@vm % [|-] := [|:-]
    \ifx\value@\empty\else\errmessage{Option [\string|-] does not assume a value}\fi
    \let@context.colsep=0%
  \else\ifx\opt@\opt@A % [A:L/C/R/LL/LC/.../*L/*C/*R], [A] := [A:CC]
    \ifx\value@\empty\let\value@=\value@CC\fi
    \ifx\value@\value@L \let@context.align=L\let@context.boxalign=L\else
    \ifx\value@\value@C \let@context.align=C\let@context.boxalign=C\else
    \ifx\value@\value@R \let@context.align=R\let@context.boxalign=R\else
    \ifx\value@\value@LL\let@context.align=L\let@context.boxalign=L\else
    \ifx\value@\value@LC\let@context.align=L\let@context.boxalign=C\else
    \ifx\value@\value@LR\let@context.align=L\let@context.boxalign=R\else
    \ifx\value@\value@CL\let@context.align=C\let@context.boxalign=L\else
    \ifx\value@\value@CC\let@context.align=C\let@context.boxalign=C\else
    \ifx\value@\value@CR\let@context.align=C\let@context.boxalign=R\else
    \ifx\value@\value@RL\let@context.align=R\let@context.boxalign=L\else
    \ifx\value@\value@RC\let@context.align=R\let@context.boxalign=C\else
    \ifx\value@\value@RR\let@context.align=R\let@context.boxalign=R\else
    \ifx\value@\value@xL                    \let@context.boxalign=L\else
    \ifx\value@\value@xC                    \let@context.boxalign=C\else
    \ifx\value@\value@xR                    \let@context.boxalign=R\else
      \errmessage{Option [A] has unknown value: "\value@"}%
    \fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi
  \else\ifx\opt@\opt@VA % [VA:T/M/C/B], [VA] := [VA:M]
    \ifx\value@\empty\let\value@=\value@M\fi
    \ifx\value@\value@T \let@context.valign=T\else
    \ifx\value@\value@M \let@context.valign=M\else
    \ifx\value@\value@C \let@context.valign=C\else
    \ifx\value@\value@B \let@context.valign=B\else
      \errmessage{Option [VA] has unknown value: "\value@"}%
    \fi\fi\fi\fi
  \else\ifx\opt@\opt@W % [W:n], [W] := [W:0], [W:?]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \ifx\value@\value@Q
      \ifx\context@\context@col\else\ifx\context@\context@cell\else\errmessage{Option [W:?] is allowed only for cells}\fi\fi
      \let@context.showW=1%
      \let\there@are@questions=1%
    \else
      \ifx\context@\context@row\errmessage{Option [W:n] is not allowed for \string\row}\fi
      \let@context.width=\value@
    \fi
  \else\ifx\opt@\opt@H % [H:n], [H] := [H:0], [H:?]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \ifx\value@\value@Q
      \ifx\context@\context@row\else\ifx\context@\context@cell\else\errmessage{Option [H:?] is allowed only for rows or cells in rows}\fi\fi
      \let@context.showH=1%
      \let\there@are@questions=1%
    \else
      \let@context.height=\value@
    \fi
  \else\ifx\opt@\opt@D % [D:n], [D] := [D:0], [D:?]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \ifx\value@\value@Q
      \ifx\context@\context@row\else\ifx\context@\context@cell\else\errmessage{Option [D:?] is allowed only for rows or cells in rows}\fi\fi
      \let@context.showD=1%
      \let\there@are@questions=1%
    \else
      \let@context.depth=\value@
    \fi
  \else\ifx\opt@\opt@M % [M:n], [M] := [M:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.multirowskip=\value@
  \else\ifx\opt@\opt@SV % [SV:n], [SV] := [SV:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.shiftV=\value@
  \else\ifx\opt@\opt@SH % [SH:n], [SH] := [SH:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.shiftH=\value@
  \else\ifx\opt@\opt@TB % [TB:n], [TB] := [TB:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingT=\value@\let@context.paddingB=\value@
  \else\ifx\opt@\opt@TBx % [TBx:n], [TBx] := [TBx:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingTx=\value@\let@context.paddingBx=\value@
  \else\ifx\opt@\opt@LR % [LR:n], [LR] := [LR:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingL=\value@\let@context.paddingR=\value@
  \else\ifx\opt@\opt@LRx % [LRx:n], [LRx] := [LRx:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingLx=\value@\let@context.paddingRx=\value@
  \else\ifx\opt@\opt@BT % [BT:n], [BT] := [BT:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingB=\value@\let@context.paddingT=\value@
  \else\ifx\opt@\opt@BTx % [BTx:n], [BTx] := [BTx:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingBx=\value@\let@context.paddingTx=\value@
  \else\ifx\opt@\opt@RL % [RL:n], [RL] := [RL:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingR=\value@\let@context.paddingL=\value@
  \else\ifx\opt@\opt@RLx % [RLx:n], [RLx] := [RLx:0]
    \ifx\value@\empty\let\value@=\value@zero\fi
    \let@context.paddingRx=\value@\let@context.paddingLx=\value@
  \else\ifx\opt@\opt@C % [CW:+], [CW:-], [CW] := [CW:-]
    \ifx\context@\context@table\else\errmessage{Option [CW:...] is allowed only for \string\Table}\fi
    \ifx\value@\empty\let\value@=\value@minus\fi
    \ifx\value@\value@plus\let\value@=1\fi\ifx\value@\value@minus\let\value@=0\fi
    \ifx\value@1\else\ifx\value@0\else\errmessage{Option [CW:...] admits only values + or -}\fi\fi
    \let@context.setcolwidths=\value@
  \else\ifx\opt@\opt@Cp % [CW+] := [CW:+]
    \ifx\context@\context@table\else\errmessage{Option [CW+] is allowed only for \string\Table}\fi
    \ifx\value@\empty\else\errmessage{Option [CW+] does not assume a value}\fi
    \let@context.setcolwidths=1%
  \else\ifx\opt@\opt@Cm % [CW-] := [CW:-]
    \ifx\context@\context@table\else\errmessage{Option [CW-] is allowed only for \string\Table}\fi
    \ifx\value@\empty\else\errmessage{Option [CW-] does not assume a value}\fi
    \let@context.setcolwidths=0%
  \else
    \let\@temp=\relax
    \ifx\opt@\opt@T\let\@temp=1\else\ifx\opt@\opt@B\let\@temp=1\else\ifx\opt@\opt@Tx\let\@temp=1\else\ifx\opt@\opt@Bx\let\@temp=1\else\fi\fi\fi\fi
    \ifx\@temp1% [T/B/Tx/Bx:n], [...] := [...:0]
      \ifx\value@\empty\let\value@=\value@zero\fi
      \edef\opt@{.padding\opt@}%
      \expandafter\let@context\opt@=\value@
    \else
      \ifx\opt@\opt@L\let\@temp=1\else\ifx\opt@\opt@R\let\@temp=1\else\ifx\opt@\opt@Lx\let\@temp=1\else\ifx\opt@\opt@Rx\let\@temp=1\else\fi\fi\fi\fi
      \ifx\@temp1% [L/R/Lx/Rx:n], [...] := [...:0]
        \ifx\value@\empty\let\value@=\value@zero\fi
        \edef\opt@{.padding\opt@}%
        \expandafter\let@context\opt@=\value@
      \else
        \ifx\value@\empty
          \errmessage{Unknown option: [\opt@]}%
        \else
          \errmessage{Unknown option: [\opt@:\value@]}%
        \fi
      \fi
    \fi
  \fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi
}

\def\inherit@opt#1.#2(#3){% Usage: \inherit@opt target.property(source)
  % Update #1.#2 using #3.#2 as default (\relax is allowed: "opt" means "optional")
  \csname get@#1\endcsname.#2->\value@@
  \ifx\value@@\relax
    \csname get@#3\endcsname.#2->\value@@
    \csname let@#1\endcsname.#2=\value@@
  \fi
}

\def\inherit@#1.#2(#3){% Usage: \inherit@ target.property(source)
  % Update #1.#2 using #3.#2 as default (\relax is not allowed)
  \inherit@opt#1.#2(#3)%
  \ifx\value@@\relax
    \ifx\allow@relax1\else\errmessage{Bug: \string\inherit@\sp@ce#1.#2(#3) set \string\relax}\fi
  \fi
}

\def\inherit@all#1(#2){% Usage: \inherit@all target(source)
  % Update all properties of #1 using the corresponding properties of #2 as defaults
  \inherit@ #1.align(#2)%
  \inherit@ #1.boxalign(#2)%
  \inherit@ #1.valign(#2)%
  \inherit@ #1.height(#2)%
  \inherit@ #1.depth(#2)%
  \inherit@ #1.multirowskip(#2)%
  \inherit@ #1.paddingL(#2)%
  \inherit@ #1.paddingR(#2)%
  \inherit@ #1.paddingLx(#2)%
  \inherit@ #1.paddingRx(#2)%
  \inherit@ #1.paddingT(#2)%
  \inherit@ #1.paddingB(#2)%
  \inherit@ #1.paddingTx(#2)%
  \inherit@ #1.paddingBx(#2)%
  \inherit@opt #1.width(#2)%
  \inherit@opt #1.shiftH(#2)%
  \inherit@opt #1.shiftV(#2)%
}

\def\process@options{\if@nexttoken[{\process@options@}{}} % Usage: \process@options[...][...]...[...]\relax
\def\process@options@[#1]{\process@option{#1}\process@options}

% Cell measurement

\def\measure@cell{% For the current cell, set cell.wd, cell.ht, cell.dp, cell.ismultiline
  \get@cell.height->\cell@height \get@cell.depth->\cell@depth
  \edef\cellstrut@start{\vrule height\cell@height ex depth\z@ width\z@}%
  \edef\cellstrut@end{\vrule height\z@ depth\cell@depth ex width\z@}%
  \get@cell.content->\cell@content
  \ifx\cell@content\empty
    \def@cell.wd={0pt}%
    \let@cell.ismultiline=\relax
    \edef@cell.ht={\cell@height ex}%
    \edef@cell.dp={\cell@depth ex}%
  \else
    \let\cell@ismultiline=\relax
    \setbox\z@\vtop{%
      \baselineskip\val@cell.multirowskip ex\relax
      \lineskip\normallineskip
      \lineskiplimit\normallineskiplimit
      \let\hfil@before=\relax\let\hfil@after=\relax
      \begingroup
        \macros@forcell
        \def\\{\unskip\egroup\global\let\cell@ismultiline=1\hbox\bgroup\ignorespaces}%
        \hbox\bgroup\cellstrut@start\cell@content\cellstrut@end\egroup
      \endgroup
    }%
    \edef@cell.wd={\the\wd\z@}%
    \edef@cell.ht={\the\ht\z@}%
    \edef@cell.dp={\the\dp\z@}%
    \let@cell.ismultiline=\cell@ismultiline
  \fi
  % cell.wd := max {natural cell width (cell.wd), user-defined cell width (cell.width)}
  \if@cell.width=\relax{}{%
    \ifdim\val@cell.wd <\lastif@value ex\relax\edef@cell.wd={\lastif@value ex}\fi
  }%
}

\def\add@height@to[#1,#2]{% Increase cell[#1,#2].rowspanheight by \dimen@
  \edef\cell@{cell[#1,#2]}%
  \get@\cell@.rowspanheight->\cell@rowspanheight
  \ifx\cell@rowspanheight\relax\def\cell@rowspanheight{0pt}\fi
  \put@\dimen@@=\cell@rowspanheight+\dimen@
  \xdef@\cell@.rowspanheight={\the\dimen@@}%
}

\def\get@cell@availheight->#1{% #1 := the height of the space (without vertical padding) available for the row-spanning cell box = rowspan height minus vertical padding
  \if@cell.rowspanstart=1{%
    \get@cell.rowspanto->\cell@rowspanto
    \edef\lastcell@{cell[\val@cell.rowspanto ,\the\col@]}%
    \put@\dimen@@@={\val@cell.rowspanheight }-{\val@cell.paddingtop }-{\val@\lastcell@.paddingbottom }%
    \edef#1{\the\dimen@@@}%
  }{%
    \errmessage{Bug: \string\get@cell@availheight\sp@ce is called for a non-rowspan-starting cell}%
  }%
}

\def\stretch@row{% For every rowspan-starting cell in the current row, if the cell does not fit, symmetrically increase .ht and .dp of the last row spanned by the cell
  \if@row.stretched=\relax{%
    \global\let\old@step=\step@ \def@step{stretch}%
    \foreach@col{%
      \if@cell.rowspanstart=1{%
        \get@cell@availheight->\cell@availheight
        % \dimen@ := height + depth of the cell content
        \if@cell.valign=M{%
          \put@\dimen@={\val@row.ht }-{\val@cell.paddingtop }%
        }{%
          \dimen@=\val@cell.ht \relax
        }%
        \advance\dimen@\val@cell.dp \relax
        % If the cell does not fit:
        \ifdim\dimen@>\cell@availheight\relax
          % \dimen@ := delta height to be added for the cell to fit
          \advance\dimen@-\cell@availheight\relax
          % Symmetrically increase .ht and .dp of the last row spanned by the cell
          \edef\lastrow@{row[\val@cell.rowspanto ]}%
          \dimen@@=\dimen@
          \divide\dimen@@2\relax
          \put@\dimen@@@={\val@\lastrow@.ht }+\dimen@@+\min@length % The last summand makes sure that the row is stretched enough even if \dimen@ was "odd" before dividing by 2
          \xdef@\lastrow@.ht={\the\dimen@@@}%
          \put@\dimen@@@={\val@\lastrow@.dp }+\dimen@@
          \xdef@\lastrow@.dp={\the\dimen@@@}%
          \advance\dimen@\min@length\relax
          % Trigger \lastrow@.onmeasure to inform the handler cells that the available space is increased by \dimen@
          \val@\lastrow@.onmeasure %
        \fi
      }{}%
    }%
    \global\let\step@=\old@step
    \global\let@row.stretched=1%
  }{}%
}

\def\dimen@inex#1{% \result@inex := dimension #1 in ex
  \begingroup % For not changing the values of \dimen@, etc.
    \dimen@=#1\relax
    \dimen@@=1ex\relax
    \multiply\dimen@ 10\relax
    \divide\dimen@\dimen@@
    \count@=\dimen@
    \count@@=\count@
    \divide\count@@10\relax
    \edef\temp@@{\the\count@@}%
    \multiply\count@@10\relax
    \advance\count@-\count@@
    \xdef\result@inex{\temp@@.\the\count@}%
  \endgroup
}

% Cell presentation

\def\present@cell@content{%
  % Left padding and fill
  \hskip\val@cell.paddingleft \relax
  \get@cell.align->\cell@align
  \ifx\cell@align C\hfill\else\ifx\cell@align R\hfill\fi\fi
  % Present the content
  \get@cell.content->\cell@content
  \get@cell.wd->\cell@width
  \ifx\cell@content\empty
    \hbox to\cell@width{\hfil}%
  \else
    % Build the cell box
    \setbox\z@\vtop to\z@{%
      \if@cell.ismultiline=1{%
        \baselineskip\val@cell.multirowskip ex\relax
        \lineskip\normallineskip
        \lineskiplimit\normallineskiplimit
        \get@cell.boxalign->\cell@boxalign
        \ifx\cell@boxalign\relax\let\cell@boxalign=\cell@align\fi
        \ifx\cell@boxalign L\let\hfil@before=\relax\let\hfil@after=\hfil\else
        \ifx\cell@boxalign C\let\hfil@before=\hfil\let\hfil@after=\hfil\else
        \ifx\cell@boxalign R\let\hfil@before=\hfil\let\hfil@after=\relax\fi\fi\fi
      }{%
        \ifx\cell@align L\let\hfil@before=\relax\let\hfil@after=\hfil\else
        \ifx\cell@align C\let\hfil@before=\hfil\let\hfil@after=\hfil\else
        \ifx\cell@align R\let\hfil@before=\hfil\let\hfil@after=\relax\fi\fi\fi
      }%
      % Insert the content with additional height at the start (first line) and depth at the end (last line)
      \edef\cellstrut@start{\vrule height\val@cell.height ex depth\z@ width\z@}%
      \edef\cellstrut@end{\vrule height\z@ depth\val@cell.depth ex width\z@}%
      \begingroup
        \macros@forcell
        \def\\{\unskip\hfil@after\egroup\hbox to\cell@width\bgroup\hfil@before\ignorespaces}%
        \hbox to\cell@width\bgroup\hfil@before\cellstrut@start\cell@content\cellstrut@end\hfil@after\egroup
      \endgroup
      \vss
    }%
    % \dimen@ := the required vertical shift of the cell box
    \dimen@=\z@
    \get@cell.valign->\cell@valign
    \ifx\cell@valign M\else
      \get@cell.ht->\cell@ht \get@row.ht->\row@ht
      \ifx\cell@valign T%
        \put@\dimen@=\cell@ht-\row@ht+{\val@cell.paddingtop }%
      \else % \cell@valign = B or C
        \if@cell.rowspanto=\relax{%
          \get@cell.paddingbottom->\cell@paddingbottom
          \put@\dimen@={\val@row.dp }-\cell@paddingbottom-{\val@cell.dp }%
          \ifx\cell@valign C%
            \put@\dimen@=\dimen@+\cell@ht-\row@ht+\cell@paddingbottom
            \divide\dimen@2\relax
          \fi
        }{%
          \get@cell@availheight->\cell@availheight
          \put@\dimen@=\cell@availheight-\row@ht-{\val@cell.dp }+{\val@cell.paddingtop }%
          \ifx\cell@valign C%
            \put@\dimen@=\dimen@+\cell@ht-\row@ht+{\val@ cell[\val@cell.rowspanto ,\the\col@].paddingbottom }%
            \divide\dimen@2\relax
          \fi
        }%
      \fi
    \fi
    \if@cell.shiftV=\relax{}{%
      \advance\dimen@\lastif@value ex\relax
    }%
    % Present the cell box
    \get@cell.shiftH->\shift@
    \ifx\shift@\relax\else\kern\shift@ ex\relax\fi
    \vbox to\z@{\vskip\dimen@\vskip-\ht\z@\box\z@\vss}%
    \ifx\shift@\relax\else\kern-\shift@ ex\relax\fi
  \fi
  % Right fill and padding
  \ifx\cell@align C\hfill\else\ifx\cell@align L\hfill\fi\fi
  \hskip\val@cell.paddingright \relax
}

% The \align@content token list population

\long\def\add@#1{\align@content\expandafter{\the\align@content#1}}

\def\add@calibrating@row{% If there is a \breaktable and the table has [CW:+], set column widths by adding a zero-height row
  \if@table.breakexists=1{\if@table.setcolwidths=1{%
    \add@{\left@vrule\global\col@0\relax}%
    \foreach@col{%
      \add@{\global\advance\col@1\relax\get@col.wd->\width@\hbox to\width@{\hfil}}%
      \ifnum\col@=\col@count
        \add@\right@vrule
      \else
        \if@col.hascolsep=1{\add@\vrule}{}%
        \add@\amp@
      \fi
    }%
    \add@\cr
  }{}}{}%
}

\def\undefined@{undefined}

\setbox\z@\vbox{\hrule} \edef\hrule@height{\the\ht\z@}
\setbox\z@\hbox{\vrule} \edef\vrule@width{\the\wd\z@}

\def\add@row{% Add the current row to \align@content and set various presentation properties of the row and its cells
  \expandafter\add@\expandafter{\expandafter\noalign\expandafter{\expandafter\global\expandafter\row@\the\row@\relax\stretch@row}}%
  % We will calculate \dimen@@ and \dimen@@@ := the maximum of the heights and depths of the cells in the row plus their paddings
  \dimen@@=\val@row.ht \relax \dimen@@@=\val@row.dp \relax % These preliminary values were calculated according to baseline-aligned cells
  % Add the optional left vertical rule and the row strut
  \add@{\left@vrule\vrule height\val@row.ht depth\val@row.dp width\z@}%
  % Add cells
  \add@{\global\col@0\relax}%
  \foreach@col{%
    \add@{\global\advance\col@1\relax}%
    % Update \dimen@@ and \dimen@@@ (the future maximum of the heights and depths of the cells plus paddings)
    \if@cell.rowspanstart=1{%
      \if@cell.valign=M{%
        \put@\dimen@={\val@cell.ht }+{\val@cell.paddingtop }\ifdim\dimen@@<\dimen@\dimen@@=\dimen@\fi
      }{}%
    }{%
      \if@cell.valign=M{%
        \put@\dimen@={\val@cell.ht }+{\val@cell.paddingtop    }\ifdim\dimen@@ <\dimen@\dimen@@ =\dimen@\fi
        \put@\dimen@={\val@cell.dp }+{\val@cell.paddingbottom }\ifdim\dimen@@@<\dimen@\dimen@@@=\dimen@\fi
      }{%
        % If the cell's full height > \dimen@@ + \dimen@@@, increase both \dimen@@ and \dimen@@@ by the half of the delta
        \put@\dimen@={\val@cell.ht }+{\val@cell.paddingtop }+{\val@cell.dp }+{\val@cell.paddingbottom }-\dimen@@-\dimen@@@
        \ifdim\dimen@>\z@
          \divide\dimen@2\relax
          \advance\dimen@@\dimen@ \advance\dimen@@@\dimen@
          \advance\dimen@@\min@length\relax % To make sure that \dimen@@ + \dimen@@@ >= the cell's full height even if \dimen@ was "odd" before dividing by 2
        \fi
      }%
    }%
    % Add the cell content
    \get@cell.parent->\cell@parent
    \ifx\cell@parent\relax
      \add@\present@cell@content
    \else
      \if@cell.firsttoken=\undefined@{}{%
        \bad@cell{is spanned (by \expandafter\cell@name\cell@parent) but is nonempty.^^J%
                  Press enter to see its first token.^^J..}%
        \show\lastif@value
      }%
      \add@\hfil
    \fi
    \ifnum\col@=\col@count\else
      \if@cell.colsep=1{\add@\vrule}{}%
      \if@cell.colspanto=\relax{\add@\amp@}{\add@\span}%
    \fi
  }%
  \edef\row@ht{\the\dimen@@}\edef\row@dp{\the\dimen@@@}%
  \let@row.ht=\row@ht\let@row.dp=\row@dp
  % Add the optional right vertical rule
  \add@\right@vrule
  \add@\cr
  % Optionally add a "line row" after the current row
  \ifnum\row@=\row@count\else\if@row.hasrowsep=1{%
    \let\row@hruleheight=\hrule@height
    \if@row.fullrowsep=1{%
      \add@{\noalign{\hrule}}%
    }{%
      \add@\left@vrule % This is just a little "dot" with the width of \vrule
      \foreach@col{%
        \if@cell.rowsep=1{\add@\hrulefill}{\add@\hfil}%
        \ifnum\col@=\col@count\add@\right@vrule\else\if@cell.colsep=1{\add@\vrule}{}\add@\amp@\fi
      }%
      \add@\cr
    }%
  }{%
    \def\row@hruleheight{0pt}%
  }\fi
  % Execute row.onmeasure event handlers: for each handler cell increase its .rowspanheight
  % by the sum row.ht + row.dp + \row@hruleheight
  \if@step{copy}{}{%
    \get@row.onmeasure->\onmeasure@
    \ifx\onmeasure@\relax\else
      \put@\dimen@=\row@ht+\row@dp+\row@hruleheight
      \onmeasure@
    \fi
  }%
}%

\def\set@col@count{%
  \ifnum\col@count=0\relax
    \col@count\col@
  \else
    \ifnum\col@count=\col@\else
      \errmessage{\string\col, \string\top, \string\row, \string\bot\sp@ce contain different number of columns: \the\col@count\sp@ce and \the\col@}%
    \fi
  \fi
}

% Cell/column definition macro (&, \cell)

\let\amp@=&
\begingroup
  \catcode`&=13\relax
  \gdef\def@amp@cell{%
    \def\cell{\advance\col@1\relax\if@nexttoken\bgroup{\cell@withargument}{\def\argument@{}\cell@afterargument}}%
    \catcode`&=13\relax\let&\cell
  }
  \gdef\def@amp@error{%
    \def\cell{\errmessage{A cell is allowed only in \string\col, \string\top, \string\row, or \string\bot}}%
    \catcode`&=13\relax\let&\cell
  }
\endgroup
\def\cell@withargument#1{\def\argument@{#1}\cell@afterargument}
\def\cell@afterargument{\if@nexttoken[{\cell@processoption}{\cell@processargument}}
\def\cell@processoption[#1]{\process@option{#1}\cell@afterargument}
\def\cell@processargument{%
  \ifx\argument@\empty
    \let\firsttoken@=\undefined@
  \else
    \expandafter\get@first@token\argument@\cell@end->\firsttoken@\relax
  \fi
  \ifx\context@\context@cell
    \let@cell.content=\argument@
    \let@cell.firsttoken=\firsttoken@
  \else
    \ifx\argument@\empty\else
      \errmessage{Column \the\col@\sp@ce specification has nonnempty content.^^J%
                  Press enter to see its first token (where \string\relax\sp@ce means a space).^^J..}%
      \show\firsttoken@
    \fi
  \fi
  \ignorespaces
}
\def\get@first@token{\futurelet\next@token\get@first@token@}
\def\get@first@token@#1\cell@end->#2{\let#2\next@token}
\def\cell@end{cell:end}

% Row definition (the main part of \top and \row)

\def\row@afterargument{\if@nexttoken[{\row@processoption}{\row@processargument}}
\def\row@processoption[#1]{\process@option{#1}\row@afterargument}
\def\row@processargument{%
  \ifx\table@part T\else
    \ifx\breaktable@defined\relax
      \def\breaktable{%
        \let@table.breakexists=1%
        \let@row.pagebreak=1%
        \edef\breaking@row{\the\row@}%
        \ifx\breaktable@passed\relax
          \def@table@frills@afterbreak
          \let\breaktable@passed=1%
        \fi
        \def\float{\errmessage{\string\float\sp@ce is not allowed after \string\breaktable}}%
        \def\before{\errmessage{\string\before\sp@ce is not allowed after \string\breaktable}}%
        \let\context@=\context@row
        \process@options
      }%
      \let\breaktable@defined=1%
    \fi
  \fi
  \let\context@=\context@cell
  \col@0\relax
  \expandafter\ignorespaces\argument@
  \set@col@count
  \def@amp@error
  \ignorespaces
}%

\def\def@table@frills@afterbreak{%
  \def@table@frill@afterbreak\name
  \def@table@frill@afterbreak\heading
  \def@table@frill@afterbreak\caption
  \def@table@frill@afterbreak\prebreaktext
  \def@table@frill@afterbreak\prebreak
  \def@table@frill@afterbreak\interbreak
  \def@table@frill@afterbreak\postbreaktext
  \def@table@frill@afterbreak\postbreak
}
\def\def@table@frill@afterbreak#1{%
  \def#1##1{%
    \count@@=\breaking@row\relax
    \if@@row[\count@@].captions=\relax{%
      \def\value@{#1{##1}}%
    }{%
      \expandafter\def\expandafter\value@\expandafter{\lastif@value#1{##1}}%
    }%
    \let@@row[\count@@].captions=\value@
  }%
}

% Table (\Table)

\def\everyTable@{}
\def\everyTable#1{\def\everyTable@{#1}}

\def\Table{\def@step{define}\let\context@=\context@table\table@beforeoptions\table@}
\def\table@{\if@nexttoken[{\table@option}{\table@main}}
\def\table@option[#1]{\process@option{#1}\table@}
\def\table@beforeoptions{%
  \begingroup
  \def@table@frills
  \def@amp@error
  \let\old@col=\col \let\old@top=\top \let\old@bot=\bot
  \def\macros@forcell{%
    \let\col=\old@col \let\top=\old@top \let\bot=\old@bot
    \def\rownumber{\the\row@}\def\colnumber{\the\col@}%
  }%
  \def\col##1{%
    \ifnum\row@=0\relax\else\errmessage{\string\col\sp@ce is not allowed after \string\top\sp@ce, \string\row, or \string\bot}\fi
    \def\col####1{\errmessage{\string\col\sp@ce may not be used twice}}%
    \let\context@=\context@col
    \col@=0\relax
    \def@amp@cell
    \ignorespaces##1%
    \set@col@count
    % todo: Temporarily redefine & (and \cell), make a \run@{\ignorespaces#1}, and if \wd\z@ != 0 do \errmessage: \col{...} contains some extra unrecognized stuff
    \def@amp@error
    \ignorespaces
  }%
  \long\def\top##1{%
    \def@amp@cell
    \def\argument@{##1}%
    \let\context@=\context@row
    \ifx\table@part\relax\else\ifx\table@part T\else\errmessage{\string\top\sp@ce is not allowed after \string\row\sp@ce or \string\bot}\fi\fi
    \let\table@part=T%
    \advance\row@1\relax
    \advance\row@count1\relax
    \advance\top@count1\relax
    \row@afterargument
  }%
  \long\def\row##1{%
    \def@amp@cell
    \def\argument@{##1}%
    \let\context@=\context@row
    \let\table@part=R%
    \advance\row@1\relax
    \advance\row@count1\relax
    \row@afterargument
  }%
  \long\def\bot##1{%
    \def@amp@cell
    \def\argument@{##1}%
    \let\context@=\context@row
    \ifx\table@part R\else\ifx\table@part B\else\errmessage{\string\bot\sp@ce is allowed only after \string\row\sp@ce or \string\bot}\fi\fi
    \let\table@part=B%
    \advance\row@1\relax
    \advance\row@count1\relax
    \ifnum\bot@start=0\relax\edef\bot@start{\the\row@}\fi
    \row@afterargument
  }%
  \def\breaktable{\errmessage{\string\breaktable\sp@ce is allowed only between ordinal rows}\fi}%
  % Default options
  \process@options[F:TBLR][|+][_-][A:C][VA:M][LR:1][LRx:.5][TB:0][TBx:.5][H:2][D:.55][M:2.4][CW+]\relax
  \expandafter\process@options\everyTable@\relax
  \let\there@are@questions=\relax
}
\def\table@main{%
  \ifx\custom@body\relax
    \col@count=0\relax
    \top@count=0\relax
    \row@count=0\relax
    \def\bot@start{0}%
    \row@=0\relax
    \let\table@part=\relax % T: \top, R: \row, B: \bot
    \let\breaktable@defined=\relax
    \let\breaktable@passed=\relax
    \def\footer@skip{\vskip 2pt plus 0.5pt minus 0.5pt}%
    \figtab@body{%
      \def@step{inherit}%
      % Inherit properties of cells other than .rowsep and .colsep (according to exact options of rows and columns)
      \foreach@row{\foreach@col{%
        \let\allow@relax=1%
        \inherit@all cell(row)% For a cell, exact options of the row have higher priority than those of the column
        \inherit@all cell(col)%
        \let\allow@relax=0%
        \inherit@all cell(table)%
      }}%
      % Inherit properties of columns
      \let\allow@relax=0%
      \foreach@col{\inherit@all col(table)}%
      % Inherit properties of rows and update rows' .hasrowsep, and cells' .rowsep, .colsep, .parent, .rowspanto, .colspanto
      \foreach@row{%
        % Inherit properties of rows
        \inherit@all row(table)%
        % Determine and remember \rowrowsep@
        \get@row.rowsep->\rowrowsep@
        \ifx\rowrowsep@\relax
          \ifnum\row@=\top@count
            \let\rowrowsep@=1
          \else
            \put@\count@=\bot@start-1%
            \ifnum\row@=\count@
              \let\rowrowsep@=1
            \else
              \get@table.rowsep->\rowrowsep@
            \fi
          \fi
        \fi
        \let\hasrowsep@=0\let\fullrowsep@=1%
        % Update cells' .rowsep, .colsep, .parent, .rowspanto, .colspanto
        \foreach@col{%
          % Update cell's .parent, determine \rowspanto@ and \colspanto@
          \get@cell.parent->\parent@
          \ifx\parent@\relax
            \get@cell.rowspanto->\rowspanto@ \get@cell.colspanto->\colspanto@
          \else
            \get@\parent@.rowspanto->\rowspanto@ \get@\parent@.colspanto->\colspanto@
          \fi
          \ifx\rowspanto@\relax\else\ifnum\rowspanto@>\row@
            % cell[\row@+1,\col@].parent := \@parent or self
            \let\value@=\parent@
            \ifx\value@\relax\edef\value@{cell[\the\row@,\the\col@]}\fi
            \put@\count@=\row@+1%
            \let@parent[\count@,\col@]=\value@
          \fi\fi
          \ifx\colspanto@\relax\else\ifnum\colspanto@>\col@
            % cell[\row@,\col@+1].parent := \@parent or self
            \let\value@=\parent@
            \ifx\value@\relax\edef\value@{cell[\the\row@,\the\col@]}\fi
            \put@\count@=\col@+1%
            \let@parent[\row@,\count@]=\value@
          \fi\fi
          % The above calls of \let@parent could change .rowspanto and .colspanto of the current cell and its parent;
          % therefore, update \rowspanto@ and \colspanto@
          \ifx\parent@\relax
            \get@cell.rowspanto->\rowspanto@ \get@cell.colspanto->\colspanto@
          \else
            \get@\parent@.rowspanto->\rowspanto@ \get@\parent@.colspanto->\colspanto@
          \fi
          \ifx\rowspanto@\relax\else\ifnum\rowspanto@=\row@\let\rowspanto@=\relax\fi\fi
          \ifx\colspanto@\relax\else\ifnum\colspanto@=\col@\let\colspanto@=\relax\fi\fi
          % Update cell.rowsep
          \ifx\rowspanto@\relax
            \get@cell.rowsep->\cellrowsep@
            \ifx\cellrowsep@\relax
              \ifnum\row@=\top@count % For the last top row, col.rowsep is ignored
                \let\cellrowsep@=\rowrowsep@
              \else
                \put@\count@=\bot@start-1%
                \ifnum\row@=\count@ % For the row before the first bottom row, col.rowsep is ignored
                  \let\cellrowsep@=\rowrowsep@
                \else
                  % For a cell, exact rowsep of the row have higher priority than that of the column
                  \if@row.rowsep=\relax{%
                    \get@col.rowsep->\colrowsep@
                    \ifx\colrowsep@\relax
                      \get@table.rowsep->\cellrowsep@
                    \else
                      \let\cellrowsep@=\colrowsep@
                    \fi
                  }{%
                    \let\cellrowsep@=\rowrowsep@
                  }%
                \fi
              \fi
            \fi
          \else
            \let\cellrowsep@=0%
          \fi
          \let@cell.rowsep=\cellrowsep@
          \ifx\cellrowsep@1\let\hasrowsep@=1\else\let\fullrowsep@=0\fi
          % Update cell.colsep and its col.hascolsep
          \ifx\colspanto@\relax
            \get@cell.colsep->\cellcolsep@
            \ifx\cellcolsep@\relax
              % For a cell, exact colsep of the row have higher priority than that of the column
              \get@row.colsep->\rowcolsep@
              \ifx\rowcolsep@\relax
                \get@col.colsep->\colcolsep@
                \ifx\colcolsep@\relax
                  \get@table.colsep->\cellcolsep@
                \else
                  \let\cellcolsep@=\colcolsep@
                \fi
              \else
                \let\cellcolsep@=\rowcolsep@
              \fi
            \fi
          \else
            \let\cellcolsep@=0%
          \fi
          \let@cell.colsep=\cellcolsep@
          \ifx\cellcolsep@1\let@col.hascolsep=1\fi
        }%
        \let@row.hasrowsep=\hasrowsep@
        \let@row.fullrowsep=\fullrowsep@
        \if@row.pagebreak=1{%
          \ifnum\row@=\row@count\errmessage{\string\breaktable\sp@ce is allowed only between ordinal rows}\fi
          \put@\count@=\row@+1%
          \ifnum\count@=\bot@start\relax\errmessage{\string\breaktable\sp@ce is allowed only between ordinal rows}\fi
          \if@@row[\count@].spanned=1{\errmessage{\string\breaktable\sp@ce is not allowed after spanning row \the\row@}}{}%
        }{}%
      }%
      % Calculate the natural sizes of cells, update again their .rowspanto and .colspanto, set all vertical and horizontal paddings, initialize row.ht and row.dp, and populate .onmeasure events of rows
      \def@step{measure}%
      \foreach@row{%
        % \row@addTx, \row@addBx := 1 if the row is such that the corresponding vertical extra padding should be added
        \let\row@addTx=\relax
        \ifnum\row@=1\relax\let\row@addTx=1\else
          \put@\count@=\top@count+1%
          \ifnum\row@=\count@\let\row@addTx=1\else
            \ifnum\row@=\bot@start\relax\let\row@addTx=1\else
              \put@\count@=\row@-1%
              \if@@row[\count@].hasrowsep=1{\let\row@addTx=1}{%
                \if@@row[\count@].pagebreak=1{\let\row@addTx=1}{}%
              }%
            \fi
          \fi
        \fi
        \let\row@addBx=\relax
        \ifnum\row@=\top@count\let\row@addBx=1\else
          \put@\count@=\bot@start-1%
          \ifnum\row@=\count@\let\row@addBx=1\else
            \ifnum\row@=\row@count\let\row@addBx=1\else
              \if@row.hasrowsep=1{\let\row@addBx=1}{%
                \if@row.pagebreak=1{\let\row@addBx=1}{}%
              }%
            \fi
          \fi
        \fi
        % Initialize row.ht and row.dp
        \put@\dimen@={\val@row.height ex}+{\val@row.paddingT ex}%
        \ifx\row@addTx1\advance\dimen@\val@row.paddingTx ex\relax\fi
        \edef@row.ht={\the\dimen@}%
        \put@\dimen@={\val@row.depth ex}+{\val@row.paddingB ex}
        \ifx\row@addBx1\advance\dimen@\val@row.paddingBx ex\relax\fi
        \edef@row.dp={\the\dimen@}%
        % Calculate the cells's sizes, update their .rowspanto and .colspanto, set horizontal paddings, and populate .onmeasure events of some subsequent rows
        \foreach@col{%
          % Set cell.paddingtop
          \dimen@=\val@cell.paddingT ex\relax
          \dimen@@=\val@cell.paddingTx ex\relax
          \ifdim\dimen@@>\z@
            \ifx\row@addTx1\advance\dimen@\dimen@@\fi
          \fi
          \edef@cell.paddingtop={\the\dimen@}%
          % Set cell.paddingbottom
          \dimen@=\val@cell.paddingB ex\relax
          \dimen@@=\val@cell.paddingBx ex\relax
          \ifdim\dimen@@>\z@
            \ifx\row@addBx1\advance\dimen@\dimen@@\fi
          \fi
          \edef@cell.paddingbottom={\the\dimen@}%
          % Set cell.wd, cell.ht, cell.dp, cell.ismultiline
          \measure@cell
          % Update the cell's .rowspanto and .colspanto
          \get@cell.parent->\parent@
          \ifx\parent@\relax
            \get@cell.rowspanto->\rowspanto@ \get@cell.colspanto->\colspanto@
          \else
            \get@\parent@.rowspanto->\rowspanto@ \get@\parent@.colspanto->\colspanto@
          \fi
          \ifx\rowspanto@\relax\else\ifnum\rowspanto@=\row@\let\rowspanto@=\relax\fi\fi
          \ifx\colspanto@\relax\else\ifnum\colspanto@=\col@\let\colspanto@=\relax\fi\fi
          % Update cell.rowspanto and cell.colspanto (for the case when the cell is both spanned and spanning)
          \let@cell.rowspanto=\rowspanto@ \let@cell.colspanto=\colspanto@
          % If the cell starts rowspanning:
          \ifx\parent@\relax\ifx\rowspanto@\relax\else
            \let@cell.rowspanstart=1%
            % For each spanned row, add the corresponding handler to the row.onmeasure event
            \edef\therow@{\the\row@}%
            \edef\handler@{\noexpand\add@height@to[\therow@,\the\col@]}%
            \foreach@Row{%
              \ifnum\row@<\therow@\relax\else\ifnum\row@>\rowspanto@\relax\else
                % row.onmeasure += \add@height@to[\therow@,\the\col@]
                \get@row.onmeasure->\onmeasure@
                \ifx\onmeasure@\relax\let\onmeasure@=\empty\fi
                \expandafter\expandafter\expandafter\def\expandafter\expandafter\expandafter\onmeasure@\expandafter\expandafter\expandafter{\expandafter\onmeasure@\handler@}%
                \let@row.onmeasure=\onmeasure@
              \fi\fi
            }%
            \expandafter\row@\therow@\relax
          \fi\fi
          % Update the initial values of row.ht and row.dp
          \if@cell.valign=M{%
            \put@\dimen@={\val@cell.ht }+{\val@cell.paddingtop }\ifdim\dimen@>\val@row.ht \relax\edef@row.ht={\the\dimen@}\fi
            \if@cell.rowspanstart=1{}{%
              \put@\dimen@={\val@cell.dp }+{\val@cell.paddingbottom }\ifdim\dimen@>\val@row.dp \relax\edef@row.dp={\the\dimen@}\fi
            }%
          }{}%
          % Set the cell's horizontal paddings
          \ifx\parent@\relax
            % Set cell.paddingleft
            \dimen@=\val@cell.paddingL ex\relax
            \dimen@@=\val@cell.paddingLx ex\relax
            \ifdim\dimen@@>\z@
              \let\do@=\relax
              \ifnum\col@=1\relax\let\do@=1\else
                \put@\count@=\col@-1%
                \if@@cell[\row@,\count@].colsep=1{\let\do@=1}{}%
              \fi
              \ifx\do@1\advance\dimen@\dimen@@\fi
            \fi
            \edef@cell.paddingleft={\the\dimen@}%
            % Set cell.paddingright
            \get@cell.colspanto->\colspanto@
            \ifx\colspanto@\relax\count@=\col@\else\count@=\colspanto@\relax\fi
            \dimen@=\val@@cell[\row@,\count@].paddingR ex\relax
            \dimen@@=\val@@cell[\row@,\count@].paddingRx ex\relax
            \ifdim\dimen@@>\z@
              \let\do@=\relax
              \ifnum\count@=\col@count\let\do@=1\else
                \if@@cell[\row@,\count@].colsep=1{\let\do@=1}{}%
              \fi
              \ifx\do@1\advance\dimen@\dimen@@\fi
            \fi
            \edef@cell.paddingright={\the\dimen@}%
          \fi
          % If the cell is neigher spanned nor col-spanning, update col.wd := max among its cells' paddingleft + wd + paddingright
          \ifnum\row@=1\relax\def@col.wd={0pt}\fi
          \ifx\colspanto@\relax\ifx\parent@\relax
            \put@\dimen@={\val@cell.paddingleft }+{\val@cell.wd }+{\val@cell.paddingright }%
            \ifdim\val@col.wd <\dimen@\edef@col.wd={\the\dimen@}\fi
          \fi\fi
        }%
      }%
      % Update all col.wd according to wide col-spanning cells
      \def@step{updatecolwd}%
      \foreach@col{%
        \foreach@row{%
          % If the cell is not spanned, col-spanning, and too wide, update .wd of its rightmost spanned column
          \if@cell.parent=\relax{%
            \get@cell.colspanto->\cell@colspanto
            \ifx\cell@colspanto\relax\else
              % \dimen@ := the sum of .wd (and vrule widths) of the spanned columns
              \dimen@=\z@
              \edef\cell@col{\the\col@}%
              \foreach@Col{%
                \ifnum\col@<\cell@col\relax\else % \cell@col <= \col@ <= \cell@colspanto
                  \advance\dimen@\val@col.wd \relax
                  \ifnum\col@<\cell@colspanto
                    \if@col.hascolsep=1{\advance\dimen@\vrule@width\relax}{}%
                  \fi
                \fi
                \ifnum\col@=\cell@colspanto\relax\break@foreach@Col\fi
              }%
              \col@=\cell@col\relax
              % To check if the cell fits in \dimen@, subtract \dimen@ from teh cell's natural width; the cell does not fit if the result is positive
              \put@\dimen@={-\dimen@}+{\val@cell.paddingleft }+{\val@cell.wd }+{\val@cell.paddingright }%
              \ifdim\dimen@>\z@
                % Increase by \dimen@ the .wd of the last column spanned by the cell
                \edef\last@col{col[\cell@colspanto]}%
                \put@\dimen@=\dimen@+{\val@\last@col.wd }%
                \edef@\last@col.wd={\the\dimen@}%
              \fi
            \fi
          }{}%
        }%
      }%
      % Apply the frame options
      \if@table.frametop=1{\let\top@hrule=\hrule}{\let\top@hrule=\relax}%
      \if@table.framebottom=1{\let\bottom@hrule=\hrule}{\let\bottom@hrule=\relax}%
      \if@table.frameleft=1{\let\left@vrule=\vrule}{\let\left@vrule=\relax}%
      \if@table.frameright=1{\let\right@vrule=\vrule}{\let\right@vrule=\relax}%
      % Build the content (also in \add@row: set various presentation properties)
      \def@step{build}%
      \align@content{\amp@##\cr}%
      \add@calibrating@row
      \let\break@happend=\relax
      \foreach@row{%
        \ifx\break@happend1\ifnum\row@=\bot@start\relax
          \def@step{copy}%
        \fi\fi
        \add@row % Various presentation properties of the row and its cells are also set in \add@row
        \ifx\table@inline\relax\if@row.pagebreak=1{%
          \xdef\old@row{\the\row@}%
          % Present the current part of the table with a copy of "bot"
          \ifnum\bot@start>0\relax
            \ifx\break@happend1%
              \def@step{copy}%
            \fi
            \foreach@Row{%
              \ifnum\row@<\bot@start\relax\else
                \add@row
              \fi
            }%
            \def@step{build}%
          \fi
          \def@step{present}%
          \ifx\break@happend\relax\before@\fi
          \inserttopcap@
          \row@=0\relax
          \align@body{\vbox{%
            \offinterlineskip
            \top@hrule
            \expandafter\halign\expandafter{\the\align@content}%
            \ifnum\bot@start>0\relax\bottom@hrule\fi
          }}%
          \ifx\prebreak@\empty\else
            \nopagebreak\footer@skip\align@caption{\captionsize@\prebreak@}%
          \fi
          \interbreak@
          \let\break@happend=1%
          \row@=\old@row\relax
          \def@step{build}%
          % Process the saved intermediate caption definitions (possible new \name, \heading, \caption, etc. for the next part of the table)
          \get@row.captions->\value@
          \def@figtab@frills@
          \def@table@frills@
          \value@
          % Process the rest rows as a new table with a copy of "top"
          \align@content{\amp@####\cr}%
          \add@calibrating@row
          \ifnum\top@count>0\relax
            \def@step{copy}%
            \foreach@Row{%
              \add@row
              \ifnum\row@=\top@count\break@foreach@Row\fi
            }%
            \def@step{build}%
          \fi
          \row@=\old@row\relax
        }{}\fi
      }%
      % Present the table (or the last part of the split table)
      \def@step{present}%
      \ifx\table@inline\relax\ifx\break@happend\relax\before@\fi\fi
      \ifx\table@inline\relax\let\box@=\vbox\else\let\box@=\vtop\fi
      \setbox\z@\box@{%
        \offinterlineskip
        \top@hrule
        \expandafter\halign\expandafter{\the\align@content}%
        \bottom@hrule
      }%
      \ifx\table@inline\relax
        \inserttopcap@
        \align@body{\box\z@}%
        \ifx\footer@\empty\else
          \nopagebreak\footer@skip\align@caption{\captionsize@\footerfont@\footer@}%
        \fi
      \else
        \box\z@
      \fi
      \noindent
      \ifx\table@inline\relax\after@\fi
    }%
  \fi
}

\def\endTable{%
  \ifx\custom@body1%
    \before@
    \ifx\table@inline\relax
      \inserttopcap@
      \align@body{\the\figtab@body}%
    \else
      \the\figtab@body
    \fi
    \noindent
    \after@
  \else
    \the\figtab@body
    % Show the sizes requested by [*:?] (in ex, approximate to 0.1 ex)
    \ifx\there@are@questions1%
      \def@step{questions}%
      \foreach@row{%
        \if@row.showH=1{%
          % Show the row's natural height
          \get@row.ht->\value@ \dimen@inex\value@
          \message{The natural height of a row is the maximum of the heights of the^^J%
                   non-row-spanning cells in the row with vertical padding.^^J%
                   Row \the\row@\sp@ce has natural height \string~\sp@ce\result@inex\sp@ce ex:}%
          \dimen@=\value@\relax\showthe\dimen@
        }{}%
        \if@row.showD=1{%
          % Show the row's natural depth
          \get@row.dp->\value@ \dimen@inex\value@
          \message{The natural depth of a row is the maximum of the depths of the^^J%
                   non-row-spanning cells in the row with vertical padding.^^J%
                   Row \the\row@\sp@ce has natural depth \string~\sp@ce\result@inex\sp@ce ex:}%
          \dimen@=\value@\relax\showthe\dimen@
        }{}%
        \foreach@col{%
          \ifnum\row@=1\relax\if@col.showW=1{%
            % Show the column natural width
            \get@col.wd->\value@ \dimen@inex\value@
            \message{The natural width of a column is the maximum of the widths of the^^J%
                     non-column-spanning cells in the column without horizontal padding.^^J%
                     Column \the\col@\sp@ce has natural width \string~\sp@ce\result@inex\sp@ce ex:}%
            \dimen@=\value@\relax\showthe\dimen@
          }{}\fi
          \if@cell.showW=1{%
            % Show the cell's natural width
            \get@cell.wd->\value@ \dimen@inex\value@
            \message{The natural width of a cell is the width of its content^^J%
                     without horizontal padding.^^J%
                     Cell \the\col@\sp@ce in row \the\row@\sp@ce has natural width \string~\sp@ce\result@inex\sp@ce ex:}%
            \dimen@=\value@\relax\showthe\dimen@
          }{}%
          \if@cell.showH=1{%
            % Show the cell's natural and (optionally) rowspan height
            \if@cell.rowspanstart=1{% Show the cell's natural and rowspan height
              \get@cell.ht->\value@  \dimen@inex\value@  \let\ht@=\result@inex
              \get@cell.rowspanheight->\value@@ \dimen@inex\value@@ \let\rowspanheight@=\result@inex
              \dimen@=\value@\relax \dimen@@=\value@@\relax
              \message{The natural height of a cell is the height of its content without^^J%
                       vertical padding. The rowspan height of a row-spanning cell^^J%
                       is the total height of the cell with vertical padding.^^J%
                       Cell \the\col@\sp@ce in row \the\row@\sp@ce has natural height \string~\sp@ce\ht@\sp@ce ex %
                       and rowspan height \string~\sp@ce\rowspanheight@\sp@ce ex:^^J%
                       > \the\dimen@\sp@ce and}\showthe\dimen@@
            }{% Show the cell's natural height
              \get@cell.ht->\value@ \dimen@inex\value@
              \message{The natural height of a cell is the height of its content^^J%
                       without vertical padding.^^J%
                       Cell \the\col@\sp@ce in row \the\row@\sp@ce has natural height \string~\sp@ce\result@inex\sp@ce ex:}%
              \dimen@=\value@\relax\showthe\dimen@
            }%
          }{}%
          \if@cell.showD=1{%
            % Show the cell's natural depth
            \get@cell.dp->\value@ \dimen@inex\value@
            \message{The natural depth of a cell is the depth of its content^^J%
                     without vertical padding.^^J%
                     Cell \the\col@\sp@ce in row \the\row@\sp@ce has natural depth \string~\sp@ce\result@inex\sp@ce ex:}%
            \dimen@=\value@\relax\showthe\dimen@
          }{}%
        }%
      }%
    \fi
    % Clean up \global assignments made in \let@parent, \add@height@to, \stretch@row
    \def@step{cleanup}%
    \foreach@row{%
      \global\let@row.ht=\relax
      \global\let@row.dp=\relax
      \global\let@row.stretched=\relax
      \foreach@col{%
        \global\let@cell.parent=\relax
        \global\let@cell.rowspanto=\relax
        \global\let@cell.colspanto=\relax
        \global\let@cell.rowspanheight=\relax
      }%
    }%
  \fi
  \def@step{undefined}%
  \endgroup
}%

% Figure (\Figure)

\def\everyFigure@{}
\def\everyFigure#1{\def\everyFigure@{#1}}

\def\Figure{\begingroup\def@figure@frills\usebotcaption\everyFigure@}
\def\endFigure{\before@\inserttopcap@\align@body{\the\figtab@body}\insertbotcap@\noindent\after@\endgroup}

% Code (\Code, \code)

\def\do@#1{\catcode`#112\relax}
\def\makeother@{\do@\ \do@\\\do@\{\do@\}\do@\$\do@\&\do@\#\do@\^\do@\_\do@\%\do@\~\do@\@}

\begingroup
  \catcode`\^^M=\active%
  \gdef\obeylines@{%
    \catcode`\^^M\active%
    \gdef^^M{\futurelet\next@\postlinebreak@}%
    \gdef\postlinebreak@{\ifx\next@^^M\hbox{}\vskip.5\baselineskip\penalty\z@\else\nopagebreak\par\fi}%
  }%
\endgroup

\def\obeyspaces@{\catcode`\ \active} % \def\obeyspaces@{\catcode`\ \active\catcode7=\active} % Changed in 1.4
\begingroup
  \obeyspaces@
  \global\let =\sp@ce
  % \lccode`\~=7\relax\lowercase{\gdef~{\nobreak\ }}% % Changed in 1.4 (since this line mystically breaks ~)
\endgroup

\def\everyCode@{}
\def\everyCode#1{\def\everyCode@{#1}}

\def\Code{%
  \par
  \begingroup
  \def@figtab@frills
  \captionleftskip{\parindent}\captionrightskip{\z@ plus 1 fil}%
  \usetopcaption
  \bodyleftskip{\parindent}\bodyrightskip{\z@}%
  \def\before@{\medskip}\def\after@{\medskip\noindent}%
  \def\body{\begingroup\makeother@\obeylines@\obeyspaces@\Code@body}%
  \def\Body{\begingroup\makeother@\obeylines@\obeyspaces@\Code@Body}%
  \everyCode@
}

\begingroup
  \catcode`|=0\catcode`\\=12
  |gdef|Code@body#1\endbody{|global|figtab@body{#1}|endCode@body}
  |gdef|Code@Body#1\endBody{|global|figtab@body{#1}|endCode@Body}
|endgroup

\def\endCode@body{\futurelet\next@\endCode@body@}
\def\endCode@Body{\futurelet\next@\endCode@Body@}
\begingroup
  \obeylines@%
  \gdef\endCode@body@#1{\ifx\next@^^M\else\errmessage{Inside \string\Code, there is no line break after \string\endbody}\fi\endgroup} % #1 eats ^^M
  \gdef\endCode@Body@#1{\ifx\next@^^M\else\errmessage{Inside \string\Code, there is no line break after \string\endBody}\fi\endgroup} % #1 eats ^^M
\endgroup

\def\endCode{%
  \before@
  \inserttopcap@
  \leftskip=\body@leftskip\relax\rightskip=\body@rightskip\relax
  {\parindent\z@\parskip\z@\tt\frenchspacing\the\figtab@body}%
  \insertbotcap@\noindent
  \after@
  \endgroup
}

\begingroup
  \obeylines@%
  \gdef\codeeolerror@{\obeylines@\def^^M{\errmessage{\string\code\sp@ce argument contains a line break}}}%
\endgroup

\def\code{\bgroup\codeeolerror@\makeother@\obeyspaces@\tt\frenchspacing\code@}
\def\code@#1{\catcode`#1\active\lccode`\~`#1\lowercase{\let~\egroup}}

\csname restore at\endcsname
\endinput