The problem is known as "positional grouping" and you'll find examples if you google for that. In 2.0 it's done using
<xsl:for-each-group group-starting-with="pattern">
which you need to apply at each level of heading.
In 1.0 the two common techniques are
(a) reduce it to a value-based grouping problem, where the grouping key is generate-id(preceding-sibling::heading[@level='1'][1]) - you can then use Muenchian grouping using this key
(b) do "sibling recursion" where you process the siblings using <xsl:apply-templates select="following-sibling::*[1]"> - I'll leave you to find examples of that in the various FAQs and tutorials.
Michael Kay
http://www.saxonica.com/
Author, XSLT Programmer's Reference and XPath 2.0 Programmer's Reference