<!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><!--DO NOT EDIT: GENERATED BY merge-function-specs.xsl--><spec xmlns:e="http://www.w3.org/1999/XSL/Spec/ElementSyntax" id="spec-top" w3c-doctype="rec" status="ext-review"><header><title>EXPath Binary Module 4.0</title><version/><w3c-designation>REC-binary-40</w3c-designation><w3c-doctype>W3C Editor's Draft</w3c-doctype><pubdate><day>01</day><month>January</month><year>2000</year></pubdate><publoc>
            <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="https://qt4cg.org/specifications/EXPath/binary-40/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">https://qt4cg.org/specifications/EXPath/binary-40/</loc>
        </publoc><altlocs><loc xmlns:xlink="http://www.w3.org/1999/xlink" href="binary-40.xml" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">Specification in XML format</loc><loc xmlns:xlink="http://www.w3.org/1999/xlink" href="function-catalog.xml" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">XML function catalog</loc></altlocs><latestloc doc="EXPath Binary Module 4.0">
            <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="https://qt4cg.org/specifications/EXPath/binary-40/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">https://qt4cg.org/specifications/EXPath/binary-40/</loc>
        </latestloc><prevrec doc="EXPath Binary Module">
            <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://expath.org/spec/binary" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">http://expath.org/spec/binary</loc>
            
        </prevrec><authlist><author role="1.0"><name>Jirka Kosek</name><email xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.saxonica.com/" xlink:type="simple" xlink:show="new" xlink:actuate="onRequest">http://kosek.com/</email></author><author role="1.0"><name>John Lumley</name><email xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.saxonica.com/" xlink:type="simple" xlink:show="new" xlink:actuate="onRequest">http://www.saxonica.com/</email></author><author role="4.0"><name>Michael Kay</name><email xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.saxonica.com/" xlink:type="simple" xlink:show="new" xlink:actuate="onRequest">http://www.saxonica.com/</email></author></authlist><errataloc xmlns:xlink="http://www.w3.org/1999/xlink" href="https://www.w3.org/XML/2017/qt-errata/xpath-functions-31-errata.html" xlink:type="simple"/><translationloc xmlns:xlink="http://www.w3.org/1999/xlink" href="https://www.w3.org/2003/03/Translations/byTechnology?technology=xpath-functions-40" xlink:type="simple"/><abstract><p>This document defines an API for XPath 4.0 to handle the manipulation of binary data.
                It defines extension functions to process data from, and generate data for, binary
                resources, including extracting subparts, searching, basic binary operations and
                conversion between binary and structured forms of XDM numbers and strings.</p><p>The document is an update of the original <bibref ref="expath-bin"/> specification,
                developed by the <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.w3.org/community/expath/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">EXPath Community
                    Group</loc>, defined for <bibref ref="xpath20"/> and published in 2013.</p><p>The principal semantic alteration is use of functional argument defaults available in
                XPath 4.0.</p><p>These functions are defined for use in <bibref ref="xpath-40"/>, <bibref ref="xquery-40"/>, <bibref ref="xslt-40"/>, and other related XML standards.
                </p><p>A summary of changes since published version 1.0 is provided
                at <specref ref="changelog"/>.</p></abstract><status><p>This version of the specification is work in progress. It is produced by the QT4
                Working Group, officially the W3C XSLT 4.0 Extensions Community Group. Individual
                functions specified in the document may be at different stages of review, reflected
                in their <term>Changes</term> notes. Comments are invited, in the form of GitHub
                issues at <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="https://github.com/qt4cg/qtspecs" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">https://github.com/qt4cg/qtspecs</loc>.</p><note role="dedication" id="dedication"><p>The publications of this community group 
<loc xmlns:xlink="http://www.w3.org/1999/xlink" href="../xquery-40/xpath-40.html#dedication" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">are dedicated</loc> to our co-chair,
Michael Sperberg-McQueen (1954–2024).</p></note></status><langusage><language id="EN">English</language></langusage><revisiondesc><p/></revisiondesc></header><body><div1 id="intro"><head>Introduction</head><changes><change>If a section of this specification has been updated since version 1.0,
                    an overview of the changes is provided, along with links to
                    navigate to the next or previous change.</change><change>Sections with significant changes are marked with a ✭ symbol in the
                    table of contents. New functions are indicated by ✚.</change></changes><p>The purpose of this document is to define functions to manipulate binary data for
                inclusion in XPath 4.0, XQuery 4.0, and XSLT 4.0. The binary data is represented by
                the type <code nobreak="false">xs:base64Binary</code> as defined by <xspecref spec="XS2" ref="base64Binary"/>.</p><p>The syntax used to call these functions and operators is specified in <bibref ref="xpath-40"/> and <bibref ref="xquery-40"/>. </p><p>This document defines several classes of functions:</p><ulist><item><p>Functions to create constant binary values and convert between the binary forms
                        and sequences of octets. </p></item><item><p>Functions to perform basic operations on binary values, such as joining,
                        selecting and searching.</p></item><item><p>Functions to perform bitwise operations.</p></item><item><p>Functions to convert between binary data and numeric values.</p></item><item><p>Functions to decode or encode strings.</p></item></ulist><p>References to specific sections of some other specifications are indicated by
                cross-document links in this document. Each such link consists of a pointer to a
                specific section followed a superscript specifying the linked document. The
                superscripts have the following meanings: FILE40 <bibref ref="expath-file-40"/>,
                FO40 <bibref ref="xpath-functions-40"/> and XS2 <bibref ref="xmlschema-2"/></p><div2 id="error.management"><head>Error codes</head><p>Error conditions are identified by a code (a QName). When such an
                    error condition is reached in the evaluation of an expression, a dynamic error
                    is thrown, with the corresponding error code (as if the standard XPath function
                    <code nobreak="false">error()</code> had been called).</p><p>In this specification these codes use the
                    <code nobreak="false">http://expath.org/ns/binary</code> namespace with a local part
                    in the form of a descriptive string, for example
                    <code role="example" nobreak="false">bin:index-out-of-range</code>. This convention is used in place of
                   the <code nobreak="false">http://www.w3.org/2005/xqt-errors</code> namespace and alpha-numeric local
                    part, e.g. <code nobreak="false">err:FOCH0004</code> used in <bibref ref="xpath-functions-40"/>. These error codes have been largely retained from the 1.0 version of the
                    EXPath specification.</p><p>Error codes are summarized in <specref ref="error-summary"/>.</p></div2><div2 id="type"><head>Binary types</head><changes><change>Binary arguments to the functions are now declared to be either
                        <code nobreak="false">xs:hexBinary</code> or <code nobreak="false">xs:base64Binary</code>, but binary
                        function results remain of type <code nobreak="false">xs:base64Binary</code>. This should
                        not cause any backward incompatibilities as casting back and forth between
                        the two representations has been possible since at least version
                        2.0</change></changes><p>XML Schema, and therefore the XDM data model, defines two primitive atomic
                types holding binary data: <xspecref spec="XS2" ref="base64Binary"/> and 
                    <xspecref spec="XS2" ref="hexBinary"/>.
                In both cases the value space is a sequence of octets; the two types differ only
                in how the binary value is converted to or from a string. Although most functions
                in this specification are not concerned with the string representation of the value,
                they need to distinguish these two types, and <code nobreak="false">xs:base64Binary</code>
                has been chosen arbitrarily as the result type for functions that return
                binary values. Where binary data is supplied as input to a function, however,
                both <code nobreak="false">xs:base64binary</code> and <code nobreak="false">xs:hexBinary</code> are accepted.</p><p><termdef id="dt-binary-value" term="binary value">The term <term>binary value</term>
                is used to mean a sequence of octets represented as an instance of 
                    <code nobreak="false">xs:base64Binary</code> or <code nobreak="false">xs:hexBinary</code>.</termdef></p><p>Conversion to and from <code nobreak="false">xs:hexBinary</code> can be performed by casting with
                    <code nobreak="false">xs:hexBinary()</code> and <code nobreak="false">xs:base64Binary()</code>.</p><note><p>Internally it is likely that implementations will use the same byte
                        array representation for both data types, and that casting
                        will merely involve a change in the type annotation; it should not 
                        require data to be copied.</p></note><p><termdef id="dt-zero-length" term="zero-length">A <termref def="dt-binary-value"/>
                that contains no octets is referred to as being <term>zero-length</term>.
                A zero-length binary value is an item, and as such is a sequence of length
                one, which is not the same thing as an empty sequence.</termdef></p></div2><div2 id="testing"><head>Test suite</head><p>A suite of test-cases for all the functions defined in this module, in <bibref ref="qt3"/> format, is defined at <bibref ref="tests.binary"/>.</p></div2><div2 id="conformance"><head>Conformance</head><p>This specification follows the general remarks on and terminology for conformance
                    given in <xspecref spec="FO40" ref="conformance"/></p><p>In this document, text labeled as an example or as a note is provided for
                    explanatory purposes and is not normative.</p></div2><div2 id="namespace-prefixes"><head>Namespaces and prefixes</head><p>The functions defined in this document are contained in the namespace
                    <code nobreak="false">http://expath.org/ns/binary</code>. The conventional
                    prefix for this namespace is <code nobreak="false">bin</code>.</p><p>This document uses the prefix <code nobreak="false">bin</code> to refer to this namespace.
                    User-written applications can choose a different prefix to refer to the
                    namespace, so long as it is bound to the correct URI.</p></div2><div2 id="func-signatures"><head>Function signatures and descriptions</head><p>Each function (or group of functions having the same name) is defined in this
                    specification using a standard proforma, full details of which can be found in
                        <xspecref spec="FO40" ref="func-signatures"/>. In particular in this version
                    (trailing) optional arguments for functions (introduced in XPath 4.0) are used
                    where appropriate in the signatures, rather than multiple-arity signatures as
                    previously. </p><p>All the functions defined in this specification are deterministic and independent
                of the static and dynamic context.</p><p>All the functions described in this specification can in principle be defined
                in terms of two primitives: <function>bin:to-octets</function> and 
                <function>bin:from-octets</function>, which convert between a <termref def="dt-binary-value"/>
                and a sequence of <code nobreak="false">xs:unsignedByte</code> values (integers in the range 0 to 255).
                In many cases functions are specified with reference to a formal equivalent
                that defines the semantics of the function directly or indirectly in terms of these
                two primitives.</p></div2></div1><div1 id="use-cases"><head>Use cases</head><p>Development of this specification was driven by requirements which some XML
                developers regularly encounter in examining or generating data which is presented in
                binary, or other non-textual forms. Some typical use cases include:</p><ulist><item><p>Getting the dimensions of an image file.</p></item><item><p>Extracting image metadata.</p></item><item><p>Processing images embedded as base64 encodings within a SOAP message.</p></item><item><p>Processing legacy text files which use different encodings in separate
                        sections.</p></item><item><p>Generating PDF files from SVG graphical data.</p></item></ulist><div2 id="example-JPEG"><head>Example – finding JPEG size</head><p>As an example, the following code reads the binary form of a JPEG image file,
                    searches for the 'Start of Frame/DCT' segment, and unpacks the relevant binary
                    sections to integer-valued attributes <code nobreak="false">height</code> and <code nobreak="false">width</code>:</p><example><eg xml:space="preserve">
&lt;xsl:variable name="binary" 
              select="file:read-binary(@href)" 
              as="xs:base64Binary"/&gt;
&lt;xsl:variable name="location" 
              select="bin:find($binary, 0, bin:hex('FFC0'))"/&gt;
&lt;size width="{bin:unpack-unsigned-integer($binary, 
                                          $location+5,
                                          2, 
                                          'most-significant-first')}"
      height="{bin:unpack-unsigned-integer($binary,
                                           $location+7,
                                           2,
                                           'most-significant-first')}"/&gt;
</eg><p>The result is an element such as:</p><eg xml:space="preserve">&lt;size width="377" height="327"/&gt;</eg></example><note><p>The <code nobreak="false">'most-significant-first'</code> argument could
                    be omitted, because it is the default. This is the numeric format used in JPEG:
                    for further information see <specref ref="endianness"/>.</p></note></div2><div2 id="example-ASN1"><head>Example – reading and writing variable length ASN.1 integers</head><changes><change>The functions in this example have been moved into a differing namespace
                        prefix (<code nobreak="false">asn:</code>) to avoid suggesting that they are part of the
                        supported function set.</change></changes><p><bibref ref="asn1"/>, used in a number of telecommunications industry standards,
                    defines a binary data syntax (the <term>basic encoding rules</term>)
                    for identifying and encoding
                    arbitrary data as streams of octets. Many of these
                    forms specify the length of data as part of their encoding. For example, 
                    an integer has a variable-length representation 
                    as a sequence of octets:</p><ulist><item><p>The first octet has the value <code nobreak="false">0x02</code> to indicate
                        that this is an integer.</p></item><item><p>Next, a variable-length length field to indicate
                            the length of the payload. (This is designed to accommodate very
                            large integers, such as those found in cryptography.)</p></item><item><p>Finally, the payload itself: the octets of the integer value in
                            most-significant-first order.</p></item></ulist><example><p>To generate such a representation for an integer from XSLT/XPath, the
                        following code might be used:</p><eg xml:space="preserve">
 &lt;xsl:function name="asn:int-octets" as="xs:integer*"&gt;
    &lt;xsl:param name="value" as="xs:integer"/&gt;
    &lt;xsl:sequence select="if ($value ne 0) 
                          then (asn:int-octets($value idiv 256), $value mod 256) 
                          else ()"/&gt;
 &lt;/xsl:function&gt;
 
 &lt;xsl:function name="asn:encode-ASN-integer" as="xs:base64Binary"&gt;
    &lt;xsl:param name="int" as="xs:integer"/&gt;
    &lt;xsl:variable name="octets" select="bin:int-octets($int)"/&gt;
    &lt;xsl:variable name="length-octets"
       select="let $l := count($octets) 
               return ( if ($l le 127) 
                        then $l 
                        else ( let $lo := asn:int-octets($l) 
                               return (128+count($lo), $lo)
                             )
                      )"/&gt;
    &lt;xsl:sequence select="bin:from-octets((2,$length-octets,$octets))"/&gt;
 &lt;/xsl:function&gt;</eg><p>The function <code nobreak="false">asn:int-octets</code> returns a sequence of all the
                        significant octets of the integer (i.e. eliminating leading zeroes) in
                        most-significant order. Examples of the encoding are: </p><eg xml:space="preserve">
 asn:encode-ASN-integer(0) → "AgA="
 asn:encode-ASN-integer(1234) → "AgIE0g=="
 asn:encode-ASN-integer(123456789123456789123456789123456789) → "Ag8XxuPAMviQRa10ZoQEXxU="
               
 asn:encode-ASN-integer(123456789.. 900 digits... 123456789) → "AoIBdgaTo....EBF8V"</eg><p>The first example requires no octets to encode zero, hence its octets are
                        <code nobreak="false">2, 0</code>. Both the second and third examples can be represented in
                        less than 128 octets (2 and 15 respectively), so length is encoded as a
                        single octet. The first three octets of the result for the last example,
                        which encodes a 900-digit integer, are: <code nobreak="false">2, 130, 1</code> indicating that
                        the data is represented by (130-128) * 256 + 1 = 513 octets and the length
                        required two octets to encode.</p><p>Decoding is a matter of compound use of the integer decoding function:</p><eg xml:space="preserve">
 &lt;xsl:function name="asn:decode-ASN-integer" as="xs:integer"&gt;
    &lt;xsl:param name="in" as="xs:base64Binary"/&gt;
    &lt;xsl:sequence
       select="let $lo := bin:unpack-unsigned-integer($in, 1, 1, 'BE') 
               return (
                  if ($lo le 127) 
                  then bin:unpack-unsigned-integer($in, 2, $lo, 'BE') 
                  else ( let $lo2 := $lo - 128, 
                             $lo3 := bin:unpack-unsigned-integer($in, 2 ,$lo2, 'BE') 
                         return bin:unpack-unsigned-integer($in, 2+$lo2, $lo3, 'BE')
                        )
               )"
    /&gt;
 &lt;/xsl:function&gt;</eg><note><p>All numbers in ASN are 'big-endian'.</p></note><p>This function is the inverse of the encoding function above:</p><eg xml:space="preserve">
 asn:decode-ASN-integer(xs:base64Binary("AgA=")) → 0
 asn:decode-ASN-integer(xs:base64Binary("AgIE0g==")) → 1234
 asn:decode-ASN-integer(xs:base64Binary("Ag8XxuPAMviQRa10ZoQEXxU=")) 
     → 123456789123456789123456789123456789              
 asn:decode-ASN-integer(xs:base64Binary("AoIBdgaTo....EBF8V")) 
     → 123456789.. 900 digits... 123456789                </eg></example></div2></div1><div1 id="id-other-operations"><head>Other Operations on Binary Values</head><p>This section provides a summary of operations on binary values beyond those 
             defined in this document.</p><div2 id="conversion"><head>Conversions</head><p>Casting is defined:</p><ulist><item><p>Between <code nobreak="false">xs:hexBinary</code> and <code nobreak="false">xs:base64Binary</code>,
                    in either direction. Since the two types have the same value space,
                    conversion is lossless, and can be expected in most implementations
                    to have very low cost.</p></item><item><p>From <code nobreak="false">xs:string</code> to <code nobreak="false">xs:hexBinary</code>
                    or <code nobreak="false">xs:base64Binary</code>. The semantics correspond to the
                    XSD rules for validation of simple types. The two binary
                    types have different lexical representation, so conversion from
                    strings requires different input.</p></item><item><p>From <code nobreak="false">xs:hexBinary</code>
                    or <code nobreak="false">xs:base64Binary</code> to <code nobreak="false">xs:string</code>. 
                        The rules are defined in <xspecref spec="XP40" ref="casting-to-string"/>. 
                        The two binary types have different lexical representation, so the output
                    in the two cases is different.</p></item></ulist></div2><div2 id="comparison"><head>Comparison</head><p>Comparison of binary values is defined using any of the value comparison
                operators <code nobreak="false">eq</code>, <code nobreak="false">ne</code>, <code nobreak="false">le</code>, <code nobreak="false">lt</code>,
                <code nobreak="false">ge</code>, or <code nobreak="false">gt</code>. It is therefore defined also for the
                general comparison operators <code nobreak="false">=</code>, <code nobreak="false">!=</code>, <code nobreak="false">&lt;=</code>, <code nobreak="false">&lt;</code>,
                <code nobreak="false">&gt;=</code>, and <code nobreak="false">&gt;</code>.</p><p>The semantics are defined in <function>op:binary-equal</function>
                and <function>op:binary-less-than</function>.</p><p>The two types <code nobreak="false">xs:hexBinary</code> and <code nobreak="false">xs:base64Binary</code>
                can be compared interchangeably.</p><p>Because binary values are ordered, sequences of binary values can be sorted
                using the function <function>fn:sort</function>, or by using the <code nobreak="false">xsl:sort</code>
                instruction in XSLT or the <code nobreak="false">order by</code> clause in XQuery.</p></div2><div2 id="numeric-representation"><head>Numeric representation</head><p>Integers can be converted to a string representation using any radix
                in the range 2 to 36 using the function <function>fn:format-integer</function>.</p><p>Conversely, strings representing an integer using any radix in the range
                2 to 36 can be converted to an integer using the function <function>fn:parse-integer</function>.</p><p>These functions do not directly involve binary values, but they can be used to
                convert between numbers and binary values by using a string representation as an intermediate
                format.</p><p>See also the functions <function>bin:pack-integer</function>, 
                    <function>bin:unpack-integer</function>, and <function>bin:unpack-unsigned-integer</function>
                defined in this specification.</p></div2><div2 id="loading"><head>Loading and saving binary data</head><changes><change>The <bibref ref="xpath-functions-40"/> function
                        <code nobreak="false">fn:binary-resource</code> has been added to the list of useful
                        functions.</change></changes><p>This module defines no specific functions for reading and writing binary data from
                    external resources, but other specifications provide some suitable mechanisms.</p><p><bibref ref="xpath-functions-40"/> provides a function to retrieve binary
                    resources:</p><example role="signature"><proto role="example" name="binary-resource" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" prefix="fn" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no" isOp="no"><arg name="filesource" type="xs:string?"/></proto></example><p>The EXPath File Module <bibref ref="expath-file-40"/> provides three functions
                    suitable for use in file-based situations:</p><example role="signature"><proto role="example" prefix="file" name="read-binary" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no" isOp="no"><arg name="file" type="xs:string"/><arg name="offset" type="xs:integer?" default="0"/><arg name="size" type="xs:integer?" default="()"/></proto></example><p>which reads binary data from an existing file, with an optional offset and size.</p><example role="signature"><proto role="example" prefix="file" name="write-binary" return-type="empty-sequence()" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no" isOp="no"><arg name="file" type="xs:string"/><arg name="value" type="xs:base64Binary"/></proto></example><p>which writes binary data into a new or existing file.</p><example role="signature"><proto role="example" prefix="file" name="append-binary" return-type="empty-sequence()" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no" isOp="no"><arg name="file" type="xs:string"/><arg name="value" type="xs:base64Binary"/></proto></example><p>which appends binary data onto the end of an existing file.</p></div2></div1><div1 id="constants"><head>Defining constants and conversions</head><p>The functions in this section can be used to define constant binary values
                or to perform simple conversions to string representations:</p><div2 id="func-bin-hex"><head>bin:hex</head><changes><change issue="1750" PR="1753" date="2025-02-03">The input string is now allowed to include embedded underscores and whitespace.</change></changes><glist><gitem><label>Summary</label><def><p>Constructs a binary value from a string of hexadecimal digits (<code nobreak="false">[0-9A-Fa-f]*</code>).</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="hex" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:string?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Any whitespace and underscore characters are stripped from <code nobreak="false">$value</code>.</p><p>
                If the length of of the resulting string is an odd number, then 
                a single <code nobreak="false">"0"</code> digit is prepended to the value, so that it contains an 
                even number of hexadecimal digits.</p><p>The resulting string is then cast to type <code nobreak="false">xs:hexBinary</code>,
            which is then cast to <code nobreak="false">xs:base64Binary</code>.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">$value ! (
  replace(., '[_\s]', '') 
  -&gt; concat(if (string-length(.) mod 2 eq 1) { "0" }, .)
  -&gt; xs:hexBinary(.)
  -&gt; xs:base64Binary(.)
)</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="non-numeric-character"/> is raised if <code nobreak="false">$value</code>
                cannot be parsed as a hexadecimal number.</p></def></gitem><gitem><label>Notes</label><def><note><p>The order of octets in the result follows the order of characters in the string.</p><p>If <code nobreak="false">$value</code> is an empty string, the result will be a
                <termref def="dt-zero-length"/> <code nobreak="false">xs:base64Binary</code> value.</p><p>When the input string has an even number of characters, this function delivers the same
                result as the expression
                <code nobreak="false">xs:base64Binary(xs:hexBinary(<emph>$string</emph>))</code>.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:hex('1122_3F4E')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">xs:base64Binary("ESI/Tg==")</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:hex('122 3F4E')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">xs:base64Binary("ASI/Tg==")</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-bin"><head>bin:bin</head><changes><change issue="1750" PR="1753" date="2025-02-03">The input string is now allowed to include embedded underscores and whitespace.</change></changes><glist><gitem><label>Summary</label><def><p>Constructs a binary value from a string of zeroes and ones (<code nobreak="false">[01]*</code>)</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="bin" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:string?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Any whitespace and underscore characters are stripped from <code nobreak="false">$value</code>.</p><p>As many zero digits (<char>U+0030</char>) as necessary are prepended
                to <code nobreak="false">$value</code> to make its string length a multiple of 8.</p><p>The string is then partitioned into substrings of length 8, and each such
            substring <var>B</var> is converted to an integer in the range 0 to 255
            by applying the function <code nobreak="false">fn:parse-integer(<var>B</var>, 2)</code>.
            The resulting sequence of integers is then converted to a <termref def="dt-binary-value"/>
            by applying the function <function>bin:from-octets</function>.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">$value ! ( (: process input if present, otherwise return () :)
     (: strip underscores and whitespace :)
     replace(., '[_\s]', '')
     (: extend to a multiple of 8 binary digits :)
  -&gt; concat(replicate("0", 7 - (string-length(.) - 1) mod 8), .)
     (: insert a separator after every 8 digits :)
  -&gt; replace(., "(.{8})", "$1/")
     (: split into groups of 8 digits :)
  -&gt; tokenize(., "/")[.]
     (: parse each group of 8 binary digits as a radix-2 integer :)
   ! parse-integer(., 2)
     (: construct a binary value from these octets :)
  -&gt; bin:from-octets(.) 
)</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="non-numeric-character"/> is raised if <code nobreak="false">$value</code>
                cannot be parsed as a binary number.</p></def></gitem><gitem><label>Notes</label><def><note><p>The order of octets in the result follows the order of characters in the string.</p><p>If <code nobreak="false">$value</code> is an empty string, the result will be a
                <termref def="dt-zero-length"/> <code nobreak="false">xs:base64Binary</code> value.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:bin('1101_0001_1101_0101')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex("D1D5")</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:bin('1 0001 1101 0101')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex("11D5")</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:bin(' 101 ')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex("05")</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-octal"><head>bin:octal</head><changes><change issue="1750" PR="1753" date="2025-02-03">The input string is now allowed to include embedded underscores and whitespace.</change><change issue="1750" PR="1753" date="2025-02-03">The way in which the value is adjusted to a whole number of octets has
                    been clarified. The rules have been made more precise, and might not
                    match the interpretation adopted by existing implementations.</change></changes><glist><gitem><label>Summary</label><def><p>Constructs a binary value from a string of octal digits (<code nobreak="false">[0-7]*</code>)</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="octal" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:string?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Otherwise:</p><olist><item><p>Any whitespace and underscore characters are stripped from <code nobreak="false">$value</code>.</p></item><item><p>Each octal digit in <code nobreak="false">$value</code> is replaced by its binary equivalent
                (<code nobreak="false">"0"</code> → <code nobreak="false">"000"</code>, <code nobreak="false">"1"</code> → <code nobreak="false">"001"</code>, 
                    <code nobreak="false">"2"</code> → <code nobreak="false">"010"</code>, <code nobreak="false">"3"</code> → <code nobreak="false">"011"</code>, 
                    <code nobreak="false">"4"</code> → <code nobreak="false">"100"</code>,
                <code nobreak="false">"5"</code> → <code nobreak="false">"101"</code>, <code nobreak="false">"6"</code> → <code nobreak="false">"110"</code>, 
                    <code nobreak="false">"7"</code> → <code nobreak="false">"111"</code>).</p></item><item><p>A maximum of two leading zero digits are stripped.</p></item><item><p>The resulting string
                is converted to a <termref def="dt-binary-value"/> by applying
                the function <function>bin:bin</function> to the result.</p></item></olist><p>The order of octets in the result follows the order of characters in the string.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">$value ! (
  replace(., '[_\s]', '') 
  =&gt;  characters()
  =!&gt; { "0": "000", "1": "001", "2": "010", "3": "011", 
        "4": "100", "5": "101", "6": "110", "7": "111" }()
  =!&gt; replace("^0?0?", "")     
  =&gt;  string-join()
  =&gt;  bin:bin()
)</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="non-numeric-character"/> is raised if <code nobreak="false">$value</code>
                cannot be parsed as an octal number.</p></def></gitem><gitem><label>Notes</label><def><note><p>The order of octets in the result follows the order of characters in the string.</p><p>If <code nobreak="false">$value</code> is a zero-length string, the result will be a
                <termref def="dt-zero-length"/> <code nobreak="false">xs:base64Binary</code> value.</p><p>The rule for padding to a whole number of octets ensures that leading zeroes
            are significant in determining the length of the final binary value, while also
            allowing a value of any length to be constructed. For example (underscores added
            for readability):</p><ulist><item><p>An input of <code nobreak="false">"0"</code> translates first to the string <code nobreak="false">"000"</code>; two
                leading zeros are removed producing <code nobreak="false">"0"</code>, which <function>bin:bin</function>
                converts to <code nobreak="false">bin:hex("00")</code>.</p></item><item><p>An input of <code nobreak="false">"155"</code> translates to the 
                    binary string <code nobreak="false">"001_101_101"</code>. The first two zeroes
                    are removed, and <function>bin:bin</function> converts the result to 
                    <code nobreak="false">bin:hex("6D")</code></p></item><item><p>An input of <code nobreak="false">"355"</code> translates to the 
                    binary string <code nobreak="false">"011_101_101"</code>. The first zero is removed,
                    and <function>bin:bin</function> converts the result to 
                    <code nobreak="false">bin:hex("ED")</code>.</p></item><item><p>An input of <code nobreak="false">"555"</code> translates to the 
                    string <code nobreak="false">"101_101_101"</code>, which <function>bin:bin</function> converts to 
                    <code nobreak="false">bin:hex("016D")</code>.</p></item><item><p>An input of <code nobreak="false">"0155"</code> translates to the 
                    string <code nobreak="false">"000_001_101_101"</code>. The first two zeros are
                    stripped giving <code nobreak="false">"0_001_101_101"</code>, which <function>bin:bin</function> converts to 
                    <code nobreak="false">bin:hex("006D")</code>.</p></item></ulist><p>The result of the expression <code nobreak="false">bin:octal("177 177 177 177")</code>
            is the 5-octet value <code nobreak="false">bin:hex("03 F9 FC FE 7F")</code> and not (as some
            users might imagine) the 4-octet value <code nobreak="false">bin:hex("7F 7F 7F 7F")</code>.
            To achieve the latter result, the expression <code nobreak="false">$value =&gt; tokenize() =&gt;
            bin:octal() =&gt; bin:join()</code> can be used.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('0')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('00')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('377')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('777')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('01FF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('0377')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('00FF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:octal('11_223_047')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('252627')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-to-octets"><head>bin:to-octets</head><changes><change>The result type is changed from <code nobreak="false">xs:integer</code> to
                <code nobreak="false">xs:unsignedByte</code>. This is made possible by the more liberal
                coercion rules defined in XPath 4.0.</change></changes><glist><gitem><label>Summary</label><def><p>Returns binary data as a sequence of integer octets.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="to-octets" return-type="xs:unsignedByte*" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If <code nobreak="false">$value</code> is a <termref def="dt-zero-length"/> 
                <termref def="dt-binary-value"/> then the empty sequence is
                returned.</p><p>Octets are returned in sequence, as instances of
                <code nobreak="false">xs:unsignedByte</code> (integers ranging from 0 to 255).</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:to-octets(bin:hex('1122AAFF')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">17, 34, 170, 255</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:to-octets(bin:hex(''))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">()</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-from-octets"><head>bin:from-octets</head><changes><change>The argument type is changed from <code nobreak="false">xs:integer</code> to
                <code nobreak="false">xs:unsignedByte</code>. This is made possible by the more liberal
                coercion rules defined in XPath 4.0. A consequence of the change
                is that supplying an out-of-range integer value is now a type error
                with the standard error code <code nobreak="false">XPTY0004</code>, rather than the
                custom error code <code role="example" nobreak="false">bin:octet-out-of-range</code> previously used.</change></changes><glist><gitem><label>Summary</label><def><p>Converts a sequence of octets into binary data.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="from-octets" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="values" type="xs:unsignedByte*"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Octets are integers from 0 to 255.</p><p>If <code nobreak="false">$values</code> is the empty sequence, the function returns a 
                <termref def="dt-zero-length"/> binary value.</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:from-octets((17, 34, 170, 255))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('1122AAFF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:from-octets(())</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('')</code></p></td></tr></tbody></table></def></gitem></glist></div2></div1><div1 id="basic-operations"><head>Basic operations</head><changes><change>The function <code nobreak="false">find-all</code> in the example for <function>bin:find</function>
                    has been moved into a differing namespace prefix (<code nobreak="false">f:</code>) to avoid
                    suggesting that it is part of the supported function set.</change></changes><div2 id="func-bin-length"><head>bin:length</head><glist><gitem><label>Summary</label><def><p>Returns the size of a binary value, measured in octets.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="length" return-type="xs:integer" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Returns the number of octets in the binary value <code nobreak="false">$value</code>.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression.</p><eg xml:space="preserve">count(bin:to-octets($value))</eg></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:length(bin:hex('FFFF'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">2</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:length(bin:hex(''))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">0</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-part"><head>bin:part</head><glist><gitem><label>Summary</label><def><p>Selects a specified range of octets from a binary value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="part" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="offset" type="xs:integer"/><arg name="size" type="xs:integer?" default="()"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Otherwise, the function returns a section of binary data starting 
                at <code nobreak="false">$offset</code>. The offset is zero-based. If
                <code nobreak="false">$size</code> is present and non-empty, the size of the returned binary data is
                <code nobreak="false">$size</code> octets. If <code nobreak="false">$size</code> is absent or empty, 
                all remaining data from <code nobreak="false">$offset</code> is returned.</p><p>The <code nobreak="false">$offset</code> is zero based.</p><p>The values of <code nobreak="false">$offset</code> and <code nobreak="false">$size</code>
                <rfc2119>must</rfc2119> be non-negative integers.</p><p>It is a dynamic error if <code nobreak="false">$offset</code> + <code nobreak="false">$size</code> is larger than the
                size of the binary data in <code nobreak="false">$value</code>.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">$value =&gt; bin:to-octets() =&gt; subsequence($offset + 1, $size) =&gt; bin:from-octets()</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + $size</code> is larger than the size of the binary data
                of <code nobreak="false">$value</code>.</p><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p></def></gitem><gitem><label>Notes</label><def><note><p>The function differs in several ways from <function>fn:subsequence</function> 
                and <function>fn:substring</function>:</p><ulist><item><p>The <code nobreak="false">$offset</code> and <code nobreak="false">$size</code> are supplied
                as integers, not doubles.</p></item><item><p>The <code nobreak="false">$offset</code> is zero-based, not one-based.</p></item><item><p>An error is raised if the selection goes outside the bounds
                of the value.</p></item></ulist></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><tbody><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:part(bin:hex('11223344556677'), 0, 4)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('11223344')</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:part(bin:hex('11223344556677'), 4)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('556677')</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:part(bin:hex('11223344556677'), 7)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('')</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:part(bin:hex('11223344556677'), 5, 0)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('')</code></p></td></tr><tr><td colspan="2" rowspan="1"><p>This example tests whether <code nobreak="false">$data</code> starts with binary content consistent
                    with a PDF file:</p></td></tr><tr><td colspan="2" rowspan="1"><eg xml:space="preserve">bin:part($data, 0, 4) eq bin:hex("25504446")</eg></td></tr><tr><td colspan="2" rowspan="1"><p><code nobreak="false">25504446</code> is the magic number for PDF files: it is the hexadecimal 
                    representation of the result of encoding the string <code nobreak="false">"%PDF"</code>
                    in UTF-8 (or US-ASCII). Note that the function
                    <function>bin:encode-string</function> can be used
                    to convert a string to its binary representation.</p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-join"><head>bin:join</head><glist><gitem><label>Summary</label><def><p>Concatenates a sequence of binary values in order.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="join" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="values" type="(xs:hexBinary | xs:base64Binary)*"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>The function returns an <code nobreak="false">xs:base64Binary</code> value created by concatenating the
                binary values in the sequence <code nobreak="false">$values</code>, in order.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression.</p><eg xml:space="preserve">$values =!&gt; bin:to-octets() =&gt; bin:from-octets()</eg></def></gitem><gitem><label>Notes</label><def><note><p>If <code nobreak="false">$values</code> is the empty sequence, the function returns a 
                <termref def="dt-zero-length"/> binary value.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:join((bin:hex('0000'), bin:hex('FFFF'), bin:hex('0000'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0000FFFF0000')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:join(())</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:join( (1 to 4) ! bin:hex('F0') )</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('F0F0F0F0')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-insert-before"><head>bin:insert-before</head><glist><gitem><label>Summary</label><def><p>Inserts octets at a given point in a binary value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="insert-before" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="offset" type="xs:integer"/><arg name="extra" type="(xs:hexBinary | xs:base64Binary)?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>If the value of <code nobreak="false">$extra</code> is the empty sequence, the function returns
                <code nobreak="false">$value</code>.</p><p>Otherwise, the function returns a binary value formed
                by concatenating the <code nobreak="false">bin:part($value, 0, $offset)</code>, then
                <code nobreak="false">$extra</code>, then <code nobreak="false">bin:part($value, $offset)</code>
                <code nobreak="false">$extra</code>, and then the remaining data from <code nobreak="false">$value</code>.</p><p>The <code nobreak="false">$offset</code> is zero based, and 
                <rfc2119>must</rfc2119> be non-negative.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">$value
=&gt; bin:to-octets() 
=&gt; insert-before($offset + 1, bin:to-octets($extra)) 
=&gt; bin:from-octets()</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset</code> is larger than the size of the binary data of
                <code nobreak="false">$value</code>.</p></def></gitem><gitem><label>Notes</label><def><note><p>If <code nobreak="false">$offset</code> is zero, the result is the binary concatenation of
                <code nobreak="false">$extra</code> and <code nobreak="false">$value</code>.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:insert-before(bin:hex('FFFF'), 1, bin:hex('00'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FF00FF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:insert-before(bin:hex('FFFF'), 0, bin:hex('00'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('00FFFF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:insert-before(bin:hex('FFFF'), 2, bin:hex('00'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FFFF00')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-pad-left"><head>bin:pad-left</head><changes><change issue="1750" PR="1753" date="2025-02-03">The argument type for <code nobreak="false">$octet</code> is changed from <code nobreak="false">xs:integer</code> to
                <code nobreak="false">xs:unsignedByte</code>. This is made possible by the more liberal
                coercion rules defined in XPath 4.0. A consequence of the change
                is that supplying an out-of-range integer value is now a type error
                with the standard error code <code nobreak="false">XPTY0004</code>, rather than the
                custom error code <code nobreak="false">bin:octet-out-of-range</code> previously used.</change></changes><glist><gitem><label>Summary</label><def><p>Returns a binary value created by padding <code nobreak="false">$value</code> on the left with <code nobreak="false">$count</code>
                occurrences of <code nobreak="false">$octet</code>.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="pad-left" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="count" type="xs:integer"/><arg name="octet" type="xs:unsigned-byte?" default="0"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Otherwise, the function returns a binary value consisting of
                <code nobreak="false">$count</code> instances of <code nobreak="false">$octet</code>, followed by <code nobreak="false">$value</code>. 
            The default for <code nobreak="false">$octet</code> is zero (0).</p><p><code nobreak="false">$size</code>
                <rfc2119>must</rfc2119> be a non-negative integer.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">(replicate($octet, $count), bin:to-octets($value)) 
=&gt; bin:from-octets()</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-left(bin:hex('FFFF'), 3)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('000000FFFF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-left(bin:hex('0000'), 3, 255)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FFFFFF0000')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-left(bin:hex(''), 8)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0000000000000000')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-pad-right"><head>bin:pad-right</head><changes><change issue="1750" PR="1753" date="2025-02-03">The argument type for <code nobreak="false">$octet</code> is changed from <code nobreak="false">xs:integer</code> to
                <code nobreak="false">xs:unsignedByte</code>. This is made possible by the more liberal
                coercion rules defined in XPath 4.0. A consequence of the change
                is that supplying an out-of-range integer value is now a type error
                with the standard error code <code nobreak="false">XPTY0004</code>, rather than the
                custom error code <code nobreak="false">bin:octet-out-of-range</code> previously used.</change></changes><glist><gitem><label>Summary</label><def><p>Returns a binary value created by padding <code nobreak="false">$value</code> on the 
                right with <code nobreak="false">$count</code> occurrences of <code nobreak="false">$octet</code>.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="pad-right" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="count" type="xs:integer"/><arg name="octet" type="xs:unsignedByte?" default="0"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Otherwise, the function returns a binary value consisting of
                <code nobreak="false">$value, followed by </code><code nobreak="false">$count</code> instances of <code nobreak="false">$octet</code>. 
            The default for <code nobreak="false">$octet</code> is zero (0).</p><p><code nobreak="false">$size</code>
                <rfc2119>must</rfc2119> be a non-negative integer.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">(bin:to-octets($value), replicate($octet, $count))
=&gt; bin:from-octets()</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-right(bin:hex('FFFF'), 3)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FFFF000000')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-right(bin:hex('0000'), 3, 255)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0000FFFFFF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pad-right(bin:hex(''), 8)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0000000000000000')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-find"><head>bin:find</head><glist><gitem><label>Summary</label><def><p>Returns the position of the first occurrence of <code nobreak="false">$search</code> within
                <code nobreak="false">$value</code>, starting at <code nobreak="false">$offset</code>.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="find" return-type="xs:integer?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="offset" type="xs:integer"/><arg name="search" type="(xs:hexBinary | xs:base64Binary)"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>Otherwise, the function returns the lowest value of <var>P</var> that is greater than
                or equal to <code nobreak="false">$offset</code>,
                such that <code nobreak="false">bin:part($value, <var>P</var>, bin:length($search)) eq <var>P</var></code>.
                If there is no such value (that is, if <code nobreak="false">$search</code> is not found), 
                the function returns the empty sequence.</p><p>If <code nobreak="false">$search</code> is <termref def="dt-zero-length"/> 
                then <code nobreak="false">$offset</code> is returned.</p><p>The value of <code nobreak="false">$offset</code>
                <rfc2119>must</rfc2119> be a non-negative integer.</p><p>The <code nobreak="false">$offset</code> is zero based.</p><p>The returned location is zero based.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">($offset to (bin:length($value) - bin:length($search)))
  [bin:part($value, 0, bin:length($search)) eq $search][1]</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset</code> is larger than the size of the binary data of
                <code nobreak="false">$value</code>.</p></def></gitem><gitem><label>Notes</label><def><note><p>Finding all the matches can be accomplished with simple recursive application:</p><eg xml:space="preserve">
&lt;xsl:function name="f:find-all" as="xs:integer*"&gt;
     &lt;xsl:param name="data" as="xs:base64Binary?"/&gt;
     &lt;xsl:param name="offset" as="xs:integer"/&gt;
     &lt;xsl:param name="pattern" as="xs:base64Binary"/&gt;
     &lt;xsl:sequence
         select="if (bin:length($pattern) eq 0) 
                 then ()
                 else let $found := bin:find($data,$offset,$pattern) 
                      return if ($found) 
                             then ($found,
                                   if ($found + 1 lt bin:length($data)) 
                                   then f:find-all($data, $found + 1, $pattern) 
                                   else ())
                             else ()"/&gt;
&lt;/xsl:function&gt;</eg></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:find((bin:hex('AABBCCDD'), 0, bin:hex('DD'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">3</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:find((bin:hex('AABBCCDD'), 0, bin:hex('FF'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">()</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:find((bin:hex('AABBCCDDBBCC'), 2, bin:hex('BBCC'))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">4</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:find((bin:hex('AABBCCDD'), 2, bin:hex(''))</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">2</code></p></td></tr></tbody></table></def></gitem></glist></div2></div1><div1 id="text-encoding"><head>Text decoding and encoding</head><p>The functions in this section convert between binary values and text strings, by applying an encoding
            that maps octets to characters.</p><p>Note that encoding names such as <code nobreak="false">"UTF-8"</code>
             are always compared without regard to case.</p><div2 id="func-bin-infer-encoding"><head>bin:infer-encoding</head><changes><change issue="2278" date="2025-11-12">New in 4.0</change></changes><glist><gitem><label>Summary</label><def><p>Examines a binary value that encodes a string, to determine the encoding and the start offset of the content.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="infer-encoding" return-type="record(encoding as xs:string, offset as xs:integer)" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/><arg name="encoding" type="xs:string?" default="()"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>The value for the encoding candidate <var>E</var> is
                <code nobreak="false">fn:upper-case($encoding)</code>, or an empty sequence if no encoding
                is supplied.</p><p>The effective encoding is determined as follows:</p><olist><item><p><code nobreak="false">UTF-8</code> if <code nobreak="false">E</code> is
                 <code nobreak="false">UTF-8</code> or absent, and if the initial octets are <code nobreak="false">xEF</code>,
                 <code nobreak="false">xBB</code> and <code nobreak="false">xBF</code>; otherwise,</p></item><item><p><code nobreak="false">UTF-16LE</code> if <var>E</var> is
                 <code nobreak="false">UTF-16</code>, <code nobreak="false">UTF-16LE</code> or absent, and if the initial octets are
                 <code nobreak="false">xFF</code> and <code nobreak="false">xFE</code>; otherwise,</p></item><item><p><code nobreak="false">UTF-16BE</code> if <var>E</var> is
                 <code nobreak="false">UTF-16</code>, <code nobreak="false">UTF-16BE</code> or absent, and if the initial octets are
                 <code nobreak="false">xFE</code> and <code nobreak="false">xFF</code>; otherwise,</p></item><item><p><code nobreak="false">UTF-16BE</code> if <var>E</var> is
                 <code nobreak="false">UTF-16</code>; otherwise,</p></item><item><p>the original value of <code nobreak="false">$encoding</code> if <var>E</var> is present;
                 otherwise,</p></item><item><p><code nobreak="false">UTF-8</code>, or a value that results from
                 implementation-defined heuristics.</p></item></olist><p>The effective start position is zero, unless the initial octets represent a
                byte order mark that has been evaluated by the above rules, in which case the
                effective start position is the zero-based offset (counting in octets) at which
                the byte order mark ends.</p><p>The function returns a record with two fields:</p><ulist><item><p><code nobreak="false">encoding</code> contains the effective encoding.</p></item><item><p><code nobreak="false">offset</code> contains the effective start position.</p></item></ulist></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="unknown-encoding"/> is raised if <code nobreak="false">$encoding</code> is
                invalid or not supported by the implementation.</p></def></gitem><gitem><label>Notes</label><def><note><p>The function is designed to be used in conjunction with <function>bin:decode-string</function>.
            Having established an encoding and a start offset, these can be used as arguments to the
            <function>bin:decode-string</function> function to decode the data.</p><p>Unlike functions such as <function>fn:unparsed-text</function>, this function does
            not have access to external data such as HTTP headers that might assist in establishing the encoding.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><tbody><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('41 42 43'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-8", "offset": 0 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('EFBBBF 41 42 43'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-8", "offset": 3 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('FEFF 0041 0042 0043'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-16BE", "offset": 2 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('0041 0042 0043'), "UTF-16BE")</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-16BE", "offset": 0 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('FFFE 4100 4200 4300'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-16LE", "offset": 2 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:infer-encoding(bin:hex('FFFE 4100 4200 4300'), 'utf-16')</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">{ "encoding": "UTF-16LE", "offset": 2 }</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve">let $input := bin:hex('FFFE 4100 4200 4300')
let ${$encoding, $offset} := bin:infer-encoding($input)
return bin:decode-string($input, $encoding, $offset)</eg></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve">"ABC"</eg></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-decode-string"><head>bin:decode-string</head><changes><change issue="2217" PR="2222" date="2025-12-01">The revised encoding rules take byte order marks into account.</change></changes><glist><gitem><label>Summary</label><def><p>Decodes a binary value as a string.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="decode-string" return-type="xs:string?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="encoding" type="xs:string?" default="()"/><arg name="offset" type="xs:integer?" default="()"/><arg name="size" type="xs:integer?" default="()"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an
                empty sequence.</p><p>If <code nobreak="false">$offset</code> or <code nobreak="false">$size</code> is non-empty, the effective value is
               computed by invoking <code nobreak="false">bin:part($value, $offset otherwise 0, $size)</code>.
               Otherwise, it is <code nobreak="false">$value</code>.</p><p>The <code nobreak="false">$encoding</code> argument, if present, follows the same rules as for the
               <code nobreak="false">encoding</code> attribute in an XML declaration. The values which an
               implementation is <rfc2119>required</rfc2119> to recognize are <code nobreak="false">UTF-8</code>,
               <code nobreak="false">UTF-16</code>, <code nobreak="false">UTF-16LE</code>, and <code nobreak="false">UTF-16BE</code>.</p><p>The effective encoding and start position is determined by invoking
               <function>bin:infer-encoding</function> with the effective value and
               <code nobreak="false">$encoding</code>.</p><p>The result of the function is a string representation of the effective value,
               starting at the effective offset, and decoded according to the effective encoding.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + $size</code> is larger than the size of the binary data
                of <code nobreak="false">$value</code>.</p><p><errorref spec="BIN40" code="invalid-encoding"/> is raised if <code nobreak="false">$encoding</code> is
                invalid for the given input.</p><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p><p><errorref spec="BIN40" code="unknown-encoding"/> is raised if <code nobreak="false">$encoding</code> is
                invalid or not supported by the implementation.</p><p><errorref spec="BIN40" code="conversion-error"/> is raised if there is an error or
                malformed input during decoding the string. Additional information about the error
                may be passed through suitable error reporting mechanisms – this is
                implementation-dependent.</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><tbody><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('41 42 43'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"ABC"</code></p><p><emph>(Whitespace in this and the following examples has been added
                        for clarity.)</emph></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('EFBBBF 41 42 43'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"ABC"</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('FFFE 4100 4200 4300'))</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"ABC"</code></p><p><emph>(Little-endian byte order is used because of the BOM at the start
                    of the data.)</emph></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('41 42 43'), offset := 1)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"BC"</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('41 42 43'), offset := 1, size := 1)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"B"</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('41 42 43 44'), 'UTF-8', 3)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"D"</code></p></td></tr><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:decode-string(bin:hex('EFBBBF 41 42 43 44'), (), 3)</code></p></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">"ABCD"</code></p></td></tr><tr><td colspan="2" rowspan="1"><p>The following tests whether the binary value <code nobreak="false">$data</code> starts
                with four octets that decode to the string <code nobreak="false">"%PDF"</code>
                (which always appears at the start of a PDF file).</p></td></tr><tr><td colspan="2" rowspan="1"><eg xml:space="preserve">bin:decode-string($data, size := 4) eq '%PDF'</eg></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-encode-string"><head>bin:encode-string</head><changes><change issue="1751" PR="1765" date="2025-02-11">The handling of byte order marks has been clarified. This may
            differ from the interpretation adopted by existing implementations.</change></changes><glist><gitem><label>Summary</label><def><p>Encodes a string into a binary value using a given encoding.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="encode-string" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:string?"/><arg name="encoding" type="xs:string?" default="'UTF-8'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>The <code nobreak="false">$encoding</code> argument is the name of an encoding. The values for 
                <code nobreak="false">$encoding</code> follow the same rules as for the 
                <code nobreak="false">encoding</code> attribute in an XML
                declaration. The only values which every implementation is
                    <rfc2119>required</rfc2119> to recognize are <code nobreak="false">UTF-8</code>,
                <code nobreak="false">UTF-16</code>, <code nobreak="false">UTF-16BE</code>, and <code nobreak="false">UTF-16LE</code>.
                The encoding <code nobreak="false">UTF-16</code> is interpreted as <code nobreak="false">UTF-16BE</code> (that is,
                most significant byte first).
            </p><p>The function returns the binary value obtained by encoding the string <code nobreak="false">$value</code> using
                the specified <code nobreak="false">$encoding</code> name.</p><p>If <code nobreak="false">$encoding</code> is omitted, <code nobreak="false">UTF-8</code> encoding is assumed.</p><p>The function does not add a byte order mark to the data. 
                But if <code nobreak="false">$value</code> includes a byte order mark (<char>U+FEFF</char>) then it is encoded in the same
            way as any other character.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="unknown-encoding"/> is raised if <code nobreak="false">$encoding</code> is
                invalid or not supported by the implementation.</p><p><errorref spec="BIN40" code="conversion-error"/>is raised if there is an error or
                malformed input during encoding the string. Additional information about the error
                may be passed through suitable error reporting mechanisms – this is
                implementation-dependent.</p></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:encode-string('ABC')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('414243')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:encode-string('ABC', 'UTF-16')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('004100420043')</code></p><p><emph>(The result has no BOM, and uses big-endian encoding.)</emph></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:encode-string(char(0xfeff) || 'ABC', 'UTF-16LE')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('fffe410042004300')</code></p><p><emph>(The result has a BOM, and uses little-endian encoding.)</emph></p></td></tr></tbody></table></def></gitem></glist></div2></div1><div1 id="numeric-packing"><head>Packing and unpacking of encoded numeric values</head><div2 id="number-rep"><head>Numeric representation</head><div3 id="endianness"><head>Octet order</head><changes><change issue="1750">
                            The <code nobreak="false">order</code> parameter of relevant functions now
                            has an <code nobreak="false">enum</code> type rather than a string type. In consequence,
                            supplying an incorrect value is now a type error 
                            (<xerrorref spec="XP" class="TY" code="0004"/>) and no longer
                            has a custom error code.
                        </change></changes><p>Packing and unpacking numeric values within binary data can be performed in
                        'most-significant-first' ('big-endian') or 'least-significant-first'
                        ('little-endian') octet order. The default is
                            <emph>'most-significant-first'</emph>. The relevant functions have an
                        optional parameter <code nobreak="false">$order</code> whose string value controls the
                        order. Least-significant-first order is indicated by any of the values
                        <code nobreak="false">least-significant-first</code>, <code nobreak="false">little-endian</code> or
                        <code nobreak="false">LE</code>. Most-significant-first order is indicated by any of the
                        values <code nobreak="false">most-significant-first</code>, <code nobreak="false">big-endian</code> or
                        <code nobreak="false">BE</code>.</p><p>The type of the <code nobreak="false">order</code> argument to the relevant function
                    is given as <code nobreak="false">enum('least-significant-first', 'little-endian', 'LE',
                    'most-significant-first', 'big-endian', 'BE')</code>.</p><p>By default, functions that convert numeric values to binary use
                    most-significant-first ordering. This corresponds to the order
                    most commonly used in network protocols, and is often referred to as
                    <term>network order</term>. If least-significant-first ordering is requested,
                    the order of octets in the result is reversed. This ordering, although
                    often used internally within computer hardware, is less commonly encountered
                    in network protocol standards: two places where it is used are the DICOM standard for
                    medical imaging, and the Bitcoin standard for cryptocurrency.</p></div3><div3 id="integer"><head>Integer representation</head><p/><p>Integers within binary data are represented, or assumed to be represented, as
                        an integral number of octets. Integers where <code nobreak="false">$length</code> is greater
                        than 8 octets (and thus not representable as a <code nobreak="false">long</code>) might be
                        expected in some situations, e.g. encryption. Whether the range of integers
                        is limited to <code nobreak="false">±2^63</code> is <xtermref spec="FO40" ref="implementation-dependent">implementation-dependent</xtermref>.</p></div3><div3 id="floating"><head>Representation of floating point numbers</head><p>When packing and unpacking floating point numbers
                        (<code nobreak="false">xs:float</code> and <code nobreak="false">xs:double</code>), the binary
                        representations are expected to correspond with those of the IEEE
                        single/double-precision 32/64-bit floating point types <bibref ref="ieee754"/>. Consequently they will occupy 4 or 8 octets when packed.</p><p>Special float and double formats are represented in IEEE format as follows:</p><ulist><item><p><code nobreak="false">INF</code> maps to
                        <code nobreak="false">0x7f80_0000</code> (float), or <code nobreak="false">0x7ff0_0000_0000_0000</code>
                        (double). </p></item><item><p><code nobreak="false">-INF</code> maps to <code nobreak="false">0xff80_0000</code> (float),
                        or <code nobreak="false">0xfff0_0000_0000_0000</code> (double).</p></item><item><p>Negative zero maps to <code nobreak="false">0x8000_0000</code> (float),
                            or <code nobreak="false">0x8000_0000_0000_0000</code> (double).</p></item><item><p><code nobreak="false">NaN</code> in the XSD and XDM type system corresponds to a 
                            <term>quiet NaN</term> as defined in <bibref ref="ieee754"/>, and therefore maps to <code nobreak="false">0x7fc0_0000</code> (float),
                            or <code nobreak="false">0x7ff8_0000_0000_0000</code> (double). These are the bit forms that
                            will be packed.</p></item><item><p>IEEE <term>signalling NaN</term> values may be encountered in binary
                        data, with the value range <code nobreak="false">0x7f80_0001</code> to
                        <code nobreak="false">0x7fbf_ffff</code> (float), or <code nobreak="false">0x7ff0_0000_0000_0001</code>
                            to <code nobreak="false">0x7ff7_ffff_ffff_ffff</code> or
                        <code nobreak="false">0xfff0_0000_0000_0001</code> to <code nobreak="false">0xfff7_ffff_ffff_ffff</code>
                        (double). Any such value encountered during unpacking will be replaced by a 
                        quiet <code nobreak="false">NaN</code>. Any low-order
                        payload in an unpacked quiet <code nobreak="false">NaN</code> is also zeroed.</p></item></ulist></div3></div2><div2 id="func-bin-pack-double"><head>bin:pack-double</head><glist><gitem><label>Summary</label><def><p>Returns the 8-octet binary representation of an <code nobreak="false">xs:double</code> value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="pack-double" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:double"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Most-significant-octet-first number representation is assumed unless the
                <code nobreak="false">$order</code> parameter specifies otherwise. Acceptable values for
                <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.</p><p>The binary representation will correspond with that of the IEEE double-precision
                64-bit floating point type <bibref ref="ieee754"/>. For more details see <specref ref="floating"/>.</p></def></gitem></glist></div2><div2 id="func-bin-pack-float"><head>bin:pack-float</head><glist><gitem><label>Summary</label><def><p>Returns the 4-octet binary representation of a <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.w3.org/TR/xmlschema-2/#float" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">float</loc> value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="pack-float" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:float"/><arg name="order" type="xs:enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Most-significant-octet-first number representation is assumed unless the
                <code nobreak="false">$order</code> parameter is specified. Acceptable values for
                <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.</p><p>The binary representation will correspond with that of the IEEE single-precision
                32-bit floating point type <bibref ref="ieee754"/>. For more details see <specref ref="floating"/>.</p></def></gitem></glist></div2><div2 id="func-bin-pack-integer"><head>bin:pack-integer</head><glist><gitem><label>Summary</label><def><p>Returns the <emph>twos-complement</emph> binary representation of an integer value
                as a binary value of a given size.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="pack-integer" return-type="xs:base64Binary" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="xs:integer"/><arg name="size" type="xs:integer"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>The function produces a binary value containing the twos-complement
            representation of <code nobreak="false">$value mod math:pow(256, $size)</code>, padded on the
            left to <code nobreak="false">$size</code> octets with zero bits if the value is positive,
            or one bits if it is negative.</p><p>The order of octets in the result is most-significant-first unless
                <code nobreak="false">$order</code> specifies otherwise.
            Acceptable values for <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.
            If least-significant-first ordering is requested then the order of octets
            in the result is reversed.</p><p>Specifying a <code nobreak="false">$size</code> of zero yields a <termref def="dt-zero-length"/>
                binary value.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p></def></gitem><gitem><label>Notes</label><def><note><p>If the integer being packed has a maximum precision of <code nobreak="false">$size</code> octets,
                then signed/unsigned versions are not necessary. If the data is considered unsigned,
                then the most significant bit of the bottom <code nobreak="false">$size</code> octets has a normal
                positive (<code nobreak="false">2^(8 *$size - 1)</code>) meaning. If it is considered to be a signed
                value, then the MSB and all the higher order, discarded bits will be '1' for a
                negative value and '0' for a positive or zero. If this function were to check the
                sizing of the supplied integer against the packing size, then any values of MSB
                and the discarded higher order bits other than 'all 1' or 'all 0' would constitute
                an error. <emph>This function does not perform such checking.</emph></p><p>Least-significant-first byte ordering simply reverses the octets in the result.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(256, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0100')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(256, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('00000100')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(65536, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0000')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(256, 2, "LE")</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('0001')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(-1, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FFFF')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(-2, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FFFFFFFE')</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:pack-integer(-2, 4, 'LE')</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">bin:hex('FEFFFFFF')</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-unpack-double"><head>bin:unpack-double</head><glist><gitem><label>Summary</label><def><p>Extracts an <code nobreak="false">xs:double</code> value
                held in IEEE format at the given offset in a binary value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="unpack-double" return-type="xs:double" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/><arg name="offset" type="xs:integer"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Extract the <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.w3.org/TR/xmlschema-2/#double" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">double</loc> value
                stored in the 8 successive octets from the <code nobreak="false">$offset</code> octet of the binary
                data of <code nobreak="false">$value</code>.</p><p>Most-significant-first number representation is assumed unless the
                <code nobreak="false">$order</code> parameter specifies otherwise. Acceptable values for
                <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.</p><p>The value of <code nobreak="false">$offset</code>
                <rfc2119>must</rfc2119> be a non-negative integer.</p><p>The <code nobreak="false">$offset</code> is zero based.</p><p>The binary representation is expected to correspond with that of the IEEE
                double-precision 64-bit floating point type <bibref ref="ieee754"/>. For more
                details see <specref ref="floating"/>.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + 8</code> (octet-length of <code nobreak="false">xs:double</code>) is
                larger than the size of the binary data of <code nobreak="false">$value</code>.</p></def></gitem></glist></div2><div2 id="func-bin-unpack-float"><head>bin:unpack-float</head><glist><gitem><label>Summary</label><def><p>Extract <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.w3.org/TR/xmlschema-2/#float" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">float</loc> value stored
                at the particular offset in binary data.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="unpack-float" return-type="xs:float" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/><arg name="offset" type="xs:integer"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Extract the <loc xmlns:xlink="http://www.w3.org/1999/xlink" href="http://www.w3.org/TR/xmlschema-2/#float" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">float</loc> value
                stored in the 4 successive octets from the <code nobreak="false">$offset</code> octet of the binary
                data of <code nobreak="false">$value</code>.</p><p>Most-significant-octet-first number representation is assumed unless the
                <code nobreak="false">$order</code> parameter specifies otherwise. Acceptable values for
                <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.</p><p>The value of <code nobreak="false">$offset</code>
                <rfc2119>must</rfc2119> be a non-negative integer.</p><p>The <code nobreak="false">$offset</code> is zero based.</p><p>The binary representation is expected to correspond with that of the IEEE
                single-precision 32-bit floating point type <bibref ref="ieee754"/>. For more
                details see <specref ref="floating"/>.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + 4</code> (octet-length of <code nobreak="false">xs:float</code>) is
                larger than the size of the binary data of <code nobreak="false">$value</code>.</p></def></gitem></glist></div2><div2 id="func-bin-unpack-integer"><head>bin:unpack-integer</head><glist><gitem><label>Summary</label><def><p>Returns a signed integer value represented by the <code nobreak="false">$size</code> octets starting
                from <code nobreak="false">$offset</code> in the input binary value.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="unpack-integer" return-type="xs:integer" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/><arg name="offset" type="xs:integer"/><arg name="size" type="xs:integer"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>The function produces an integer represented by the binary value
                <code nobreak="false">bin:part($value, $offset, $size)</code>. This is interpreted
            as a twos-complement representation of a signed integer, with the most significant
            octet first unless the <code nobreak="false">$order</code> option specifies otherwise.</p><p>Acceptable values for <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.
            If least-significant-first ordering is requested then the order of octets
            in the input is reversed.</p><p>The values of <code nobreak="false">$offset</code> and <code nobreak="false">$size</code>
                <rfc2119>must</rfc2119> be non-negative integers.</p><p><code nobreak="false">$offset</code> is zero based.</p><p>Specifying a <code nobreak="false">$size</code> of zero yields the integer <code nobreak="false">0</code>.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + $size</code> is larger than the size of the binary data
                of <code nobreak="false">$value</code>.</p><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p><p><errorref spec="BIN40" code="integer-too-large"/> is raised if <code nobreak="false">$size</code> is
                too large for the implementation-defined maximum integer size.</p></def></gitem><gitem><label>Notes</label><def><note><p>For discussion on integer range see <specref ref="integer"/>.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('0100'), 0, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">256</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('00000100'), 0, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">256</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('FFFF'), 0, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">-1</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('00FFFFFFFF'), 1, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">-1</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('FEFF'), 0, 2, "LE")</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">-2</code></p></td></tr></tbody></table></def></gitem></glist></div2><div2 id="func-bin-unpack-unsigned-integer"><head>bin:unpack-unsigned-integer</head><glist><gitem><label>Summary</label><def><p>Returns an unsigned integer value represented by the <code nobreak="false">$size</code> octets
                starting from <code nobreak="false">$offset</code> in the input binary representation.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="unpack-unsigned-integer" return-type="xs:integer" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)"/><arg name="offset" type="xs:integer"/><arg name="size" type="xs:integer"/><arg name="order" type="enum('least-significant-first', 'little-endian', 'LE',                     'most-significant-first', 'big-endian', 'BE')?" default="'most-significant-first'"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>The function produces an integer represented by the binary value
                <code nobreak="false">bin:part($value, $offset, $size)</code>. This is interpreted
            as a representation of an unsigned integer, with the most significant
            octet first unless the <code nobreak="false">$order</code> option specifies otherwise.</p><p>Acceptable values for <code nobreak="false">$order</code> are described in <specref ref="endianness"/>.
            If least-significant-first ordering is requested then the order of octets
            in the input is reversed.</p><p>The values of <code nobreak="false">$offset</code> and <code nobreak="false">$size</code>
                <rfc2119>must</rfc2119> be non-negative integers.</p><p><code nobreak="false">$offset</code> is zero based.</p><p>Specifying a <code nobreak="false">$size</code> of zero yields the integer <code nobreak="false">0</code>.</p></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="index-out-of-range"/> is raised if <code nobreak="false">$offset</code> is
                negative or <code nobreak="false">$offset + $size</code> is larger than the size of the binary data
                of <code nobreak="false">$value</code>.</p><p><errorref spec="BIN40" code="negative-size"/> is raised if <code nobreak="false">$size</code> is
                negative.</p><p><errorref spec="BIN40" code="integer-too-large"/> is raised if <code nobreak="false">$size</code> is
                too large for the implementation-defined maximum integer size.</p></def></gitem><gitem><label>Notes</label><def><note><p>For discussion on integer range see <specref ref="integer"/>.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><thead><tr><th rowspan="1" colspan="1">Expression</th><th rowspan="1" colspan="1">Result</th></tr></thead><tbody><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-unsigned-integer(bin:hex('0100'), 0, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">256</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-unsigned-integer(bin:hex('00000100'), 0, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">256</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-unsigned-integer(bin:hex('FFFF'), 0, 2)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">65535</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-unsigned-integer(bin:hex('00FFFFFFFF'), 1, 4)</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">4294967295</code></p></td></tr><tr><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve"><code nobreak="false">bin:unpack-integer(bin:hex('FEFF'), 0, 2, "LE")</code></eg></td><td valign="top" rowspan="1" colspan="1"><p><code nobreak="false">65279</code></p></td></tr></tbody></table></def></gitem></glist></div2></div1><div1 id="bitwise"><head>Bitwise operations</head><div2 id="func-bin-or"><head>bin:or</head><glist><gitem><label>Summary</label><def><p>Returns the bitwise OR of two binary values.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="or" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value1" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="value2" type="(xs:hexBinary | xs:base64Binary)?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If either argument is the empty sequence, an empty sequence is returned.</p><p>Otherwise, <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> must have the same length.</p><p>The function converts <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> to sequences
            of bits <var>A</var> and <var>B</var>, and returns a binary value in which 
                the <var>N</var>th bit is set to 1 if either or both of the <var>N</var>th bit of <var>A</var>
            and the <var>N</var>th bit of <var>B</var> are 1, and is set to 0 otherwise.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">let $octet-chars := fn($x) {
  bin:to-octets($x) 
  =!&gt; format-integer('2^xxxxxxxx') 
  =&gt;  string-join()
  =&gt;  characters()
}
let $A := $octet-chars($value1)
let $B := $octet-chars($value2)
let $R := for-each-pair($A, $B, fn($p, $q) {
  if ($p eq '1' or $q eq '1') then '1' else '0'
})
return bin:bin(string-join($R))</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="differing-length-arguments"/> is raised if the input
                arguments are of differing length.</p></def></gitem></glist></div2><div2 id="func-bin-xor"><head>bin:xor</head><glist><gitem><label>Summary</label><def><p>Returns the bitwise exclusive-OR of two binary arguments.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="xor" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value1" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="value2" type="(xs:hexBinary | xs:base64Binary)?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If either argument is the empty sequence, an empty sequence is returned.</p><p>Otherwise, <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> must have the same length.</p><p>The function converts <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> to sequences
            of bits <var>A</var> and <var>B</var>, and returns a binary value in which 
                the <var>N</var>th bit is set to 1 if the <var>N</var>th bit of <var>A</var>
            differs from the <var>N</var>th bit of <var>B</var>, and is set to 0 if they are
                the same.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">let $octet-chars := fn($x) {
  bin:to-octets($x) 
  =!&gt; format-integer('2^xxxxxxxx') 
  =&gt;  string-join()
  =&gt;  characters()
}
let $A := $octet-chars($value1)
let $B := $octet-chars($value2)
let $R := for-each-pair($A, $B, fn($p, $q) {
  if ($p ne $q) then '1' else '0'
})
return bin:bin(string-join($R))</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="differing-length-arguments"/> is raised if the input
                arguments are of differing length.</p></def></gitem></glist></div2><div2 id="func-bin-and"><head>bin:and</head><glist><gitem><label>Summary</label><def><p>Returns the bitwise AND of two binary arguments.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="and" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value1" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="value2" type="(xs:hexBinary | xs:base64Binary)?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If either argument is the empty sequence, an empty sequence is returned.</p><p>Otherwise, <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> must have the same length.</p><p>The function converts <code nobreak="false">$value1</code> and <code nobreak="false">$value2</code> to sequences
            of bits <var>A</var> and <var>B</var>, and returns a binary value in which 
                the <var>N</var>th bit is set to 1 if both the <var>N</var>th bit of <var>A</var>
            and the <var>N</var>th bit of <var>B</var> are 1, and is set to 0 otherwise.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">let $octet-chars := fn($x) {
  bin:to-octets($x) 
  =!&gt; format-integer('2^xxxxxxxx') 
  =&gt;  string-join()
  =&gt;  characters()
}
let $A := $octet-chars($value1)
let $B := $octet-chars($value2)
let $R := for-each-pair($A, $B, fn($p, $q) {
  if ($p eq '1' and $q eq '1') then '1' else '0'
})
return bin:bin(string-join($R))</eg></def></gitem><gitem><label>Error Conditions</label><def><p><errorref spec="BIN40" code="differing-length-arguments"/> is raised if the input
                arguments are of differing length.</p></def></gitem></glist></div2><div2 id="func-bin-not"><head>bin:not</head><glist><gitem><label>Summary</label><def><p>Returns the "bitwise not" of a binary argument.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="not" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>Returns "bitwise not" applied to <code nobreak="false">$value</code>.</p><p>If the argument is the empty sequence, an empty sequence is returned.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">let $octet-chars := fn($x) {
  bin:to-octets($x) 
  =!&gt; format-integer('2^xxxxxxxx') 
  =&gt;  string-join()
}
return (
  $octet-chars($value)
  =&gt; translate('01', '10')
  =&gt; bin:bin()
)</eg></def></gitem></glist></div2><div2 id="func-bin-shift"><head>bin:shift</head><glist><gitem><label>Summary</label><def><p>Shift the bits of a binary value left or right.</p></def></gitem><gitem><label>Signature</label><def><example role="signature"><proto isOp="no" prefix="bin" name="shift" return-type="xs:base64Binary?" returnEmptyOk="no" returnSeq="no" returnVaries="no" isSchema="no" isDatatype="no" isSpecial="no"><arg name="value" type="(xs:hexBinary | xs:base64Binary)?"/><arg name="by" type="xs:integer"/></proto></example></def></gitem><gitem><label>Properties</label><def><p>This function is <xtermref spec="FO40" ref="dt-deterministic">deterministic</xtermref>, <xtermref spec="FO40" ref="dt-context-independent">context-independent</xtermref>,  and <xtermref spec="FO40" ref="dt-focus-independent">focus-independent</xtermref>. </p></def></gitem><gitem><label>Rules</label><def><p>If the value of <code nobreak="false">$value</code> is the empty sequence, the function returns an empty
                sequence.</p><p>In other cases the length of the result is always the same as the
                length of <code nobreak="false">$value</code>.</p><p>If <code nobreak="false">$by</code> is positive then bits are shifted <code nobreak="false">$by</code> times to the
                left. The first <code nobreak="false">$by</code> bits are discarded, and <code nobreak="false">$by</code>
                zero bits are injected at the end.</p><p>If <code nobreak="false">$by</code> is negative then bits are shifted <code nobreak="false">-$by</code> times to the
                right. The last <code nobreak="false">-$by</code> bits are discarded, and <code nobreak="false">-$by</code>
                zero bits are injected at the start.</p><p>If <code nobreak="false">$by</code> is zero, the result is identical to <code nobreak="false">$value</code>.</p><p>If <code nobreak="false">abs($by)</code> is greater than the bit-length of <code nobreak="false">$value</code> then an
                all-zeros result, of the same length as <code nobreak="false">$value</code>, is returned.</p><p><code nobreak="false">abs($by)</code> can be greater than 8, implying multi-byte shifts.</p></def></gitem><gitem><label>Formal Equivalent</label><def><p>The effect of the function is equivalent to the result of the following XPath expression, except in error cases.</p><eg xml:space="preserve">let $string := (
  bin:to-octets($value) 
  =!&gt; format-integer('2^xxxxxxxx') 
  =&gt;  string-join()
)
let $len := string-length($string)
let $shifted := if (abs($by) &gt;= $len) then (
  string-join(replicate('0', $len))
) else if ($by &gt;= 0) then (
  substring($string, $by + 1) || replicate('0', $by)
) else (
  replicate('0', -$by) || substring($string, 1, -$by)
)
return bin:bin($shifted)</eg></def></gitem><gitem><label>Notes</label><def><note><p>Bit shifting across byte boundaries implies “big-endian treatment”, i.e. the leftmost
                (high-order) bit when shifted left becomes the low-order bit of the preceding
                byte.</p></note></def></gitem><gitem><label>Examples</label><def role="example"><table role="medium"><tbody><tr class="testdiv"><th valign="top" rowspan="1" colspan="1">Expression:</th><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve">bin:shift(bin:hex("000001"), 17)</eg></td></tr><tr><th valign="top" rowspan="1" colspan="1">Result:</th><td valign="top" rowspan="1" colspan="1"><eg xml:space="preserve">bin:hex("020000")</eg></td></tr></tbody></table></def></gitem></glist></div2></div1></body><back><div1 id="biblio"><head>References</head><div2 id="normative-biblio"><head>Normative references</head><blist><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="expath-bin" key="EXPath Binary 1.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">
                        <loc href="http://expath.org/spec/binary" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">Binary Module 1.0</loc>. Jirka
                        Kosek and John Lumley, editors. EXPath Module. 3 December 2013.</bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="expath-file-40" key="EXPath File 4.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"/><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="ieee754" key="IEEE 754-1985" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">IEEE Standard for Binary Floating-Point
                        Arithmetic. See <loc href="http://standards.ieee.org/reading/ieee/std_public/description/busarch/754-1985_desc.html" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">http://standards.ieee.org/reading/ieee/std_public/description/busarch/754-1985_desc.html</loc></bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="ieee754-2019" key="IEEE 754-2019" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">IEEE. <emph>IEEE Standard for
                            Floating-Point Arithmetic.</emph>
                    </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xpath20" key="XML Path Language (XPath) 2.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"/><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xpath-functions-40" key="XQuery and XPath Functions and Operators 4.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"/><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xpath-40" key="XPath 4.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">
                        
                    </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xslt-40" key="XSL Transformations (XSLT) Version 4.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">
                        <emph>CITATION: T.B.D.</emph>
                    </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xpath-datamodel-40" key="XQuery and XPath Data Model (XDM) 4.0" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"/><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xquery-40" key="XQuery 4.0: An XML Query Language" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">
                        <emph>CITATION: T.B.D.</emph>
                    </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="xmlschema-2" key="XML Schema Part 2: Datatypes Second Edition" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"> XML
                        Schema Part 2: Datatypes Second Edition, Oct. 28 2004. Available at: <loc href="http://www.w3.org/TR/xmlschema-2/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">http://www.w3.org/TR/xmlschema-2/</loc>
                    </bibl></blist></div2><div2 id="non-normative-biblio"><head>Non-normative references</head><blist><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="asn1" key="ASN.1" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest"> OSI networking and system aspects – Abstract Syntax
                        Notation One (ASN.1) – see <loc href="http://www.itu.int/ITU-T/studygroups/com17/languages/X.690-0207.pdf" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">ASN.1 encoding rules: Specification of Basic Encoding Rules (BER),
                            Canonical Encoding Rules (CER) and Distinguished Encoding Rules (DER)
                        </loc>. ITU-T X.690 (07/2002) </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="tests.binary" key="Test-suite" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">The test suite for this module, using
                        QT3 format, is in the EXPath repository <loc href="http://github.com/expath/expath-cg/tree/master/tests/qt3/binary" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">http://github.com/expath/expath-cg</loc> in the directory
                        tests/qt3/binary/</bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="qt3" key="QT3" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">
                        <loc href="http://dev.w3.org/2011/QT3-test-suite/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">XML Query Test
                            Suite</loc>. W3C 21 June 2013. </bibl><bibl xmlns:xlink="http://www.w3.org/1999/xlink" id="expath" key="EXPath" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">EXPath: Collaboratively Defining Open Standards
                        for Portable XPath Extensions. <loc href="http://expath.org/" xlink:type="simple" xlink:show="replace" xlink:actuate="onRequest">http://expath.org/</loc>.</bibl></blist></div2></div1><div1 id="error-summary"><head>Error summary</head><p>The error text provided with these errors is non-normative.</p><error-list><error spec="BIN40" code="differing-length-arguments"><p>The two arguments to a bitwise operation are of differing lengths.</p></error><error spec="BIN40" code="index-out-of-range"><p>Attempting to retrieve data outside the meaningful range of a binary data
                        type.</p></error><error spec="BIN40" code="integer-too-large"><p>Attempting to unpack a signed or unsigned integer whose length exceeds
                        the implementation-defined maximum.</p></error><error spec="BIN40" code="invalid-encoding"><p>The specified encoding is invalid.</p></error><error spec="BIN40" code="negative-size"><p>Size of binary portion, required numeric size or padding is negative.</p></error><error spec="BIN40" code="non-numeric-character"><p>Wrong character in binary 'numeric constructor' string.</p></error><error spec="BIN40" code="unknown-encoding"><p>The specified encoding is not supported.</p></error><error spec="BIN40" code="conversion-error"><p>Error in converting to/from a string.</p></error></error-list></div1><inform-div1 id="glossary"><head>Glossary</head><?glossary?></inform-div1><inform-div1 id="other-functions"><head>Other Functions</head><p>This Appendix describes some sources of functions or operators that fall outside the
                scope of the function library defined in this specification. It includes both
                function specifications and function implementations. Inclusion of a function in
                this appendix does not constitute any kind of recommendation or endorsement; neither
                is omission from this appendix to be construed negatively. This Appendix does not
                attempt to give any information about licensing arrangements for these function
                specifications or implementations.</p><div2 id="functions-in-other-w3c-specs"><head>XPath Functions and Operators Defined in Other W3C Recommendations</head><p>A number of W3C Recommendations make use of XPath, and in some cases such
                    Recommmendations define additional functions to be made available when XPath is
                    used in a specific host language.</p><div3 id="functions-defined-in-XPathFO"><head>Functions and Operators Defined in XPath and XQuery Functions and
                        Operators</head><p>Of particular interest to this specification, <bibref ref="xpath-functions-40"/> defines<ulist><item><p>Comparison operators
                                    on <code nobreak="false">xs:hexBinary</code> and <code nobreak="false">xs:base64Binary</code>
                                    values, defining the semantics of the <code nobreak="false">eq</code>,
                                    <code nobreak="false">ne</code>, <code nobreak="false">lt</code> and <code nobreak="false">ge</code> operators
                                    applied to binary data. Each returns a boolean
                                    value.</p></item><item><p>A function to retrieve the value of a
                                    binary resource</p></item></ulist></p><table role="data"><thead><tr><th rowspan="1" colspan="1">Function name</th><th rowspan="1" colspan="1">Availability</th><th rowspan="1" colspan="1">Notes</th></tr></thead><tbody><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FO40" ref="func-binary-equal"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Returns <code nobreak="false">true</code> if both binary values contain the same
                                    octet sequence.</td></tr><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FO40" ref="func-binary-less-than"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Returns <code nobreak="false">true</code> if the first argument is less than the
                                    second.</td></tr><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FO40" ref="func-binary-resource"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Returns a resource as <code nobreak="false">xs:base64Binary</code>.</td></tr></tbody></table></div3></div2><div2 id="functions-defined-by-community-groups"><head>Functions Defined by Community Groups</head><div3 id="functions-defined-in-EXPathFile"><head>Functions Defined in EXPath File</head><p>Of particular interest to this specification, <bibref ref="expath-file-40"/>
                        defines the following functions for input and output of
                        <code nobreak="false">xs:base64Binary</code> values:</p><table role="data"><thead><tr><th rowspan="1" colspan="1">Function name</th><th rowspan="1" colspan="1">Availability</th><th rowspan="1" colspan="1">Notes</th></tr></thead><tbody><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FILE40" ref="func-file-read-binary"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Returns the content of a file in its Base64 representation.</td></tr><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FILE40" ref="func-file-write-binary"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Writes a Base64 item as binary data to a file.</td></tr><tr><td rowspan="1" colspan="1">
                                    <xspecref spec="FILE40" ref="func-file-append-binary"/>
                                </td><td rowspan="1" colspan="1">XPath4.0+</td><td rowspan="1" colspan="1">Appends a Base64 item as binary data to a file.</td></tr></tbody></table></div3></div2></inform-div1><inform-div1 id="changelog" diff="chg" at="2024-11-22"><head>Changes since version 1.0</head><div2 id="changes-summary"><head>Summary of Changes</head><?change-log?></div2><div2 id="changes-to-function-signatures"><head>Changes to Function Signatures</head><olist><item><p>The function signatures of all the specified signatures now use the
                            'optional argument' syntax of XPath 4.0 where appropriate, rather than
                            giving several signatures of differing arity. Other than that, no
                            intended change to the semantics of the functions are assumed.</p></item></olist></div2><div2 id="editorial-changes"><head>Editorial Changes</head><p>These changes are not highlighted in the change-marked version of the
                    specification.</p><olist><item><p>The example functions in <specref ref="example-ASN1"/> have been moved
                            into a differing namespace prefix (<code nobreak="false">asn:</code>) to avoid
                            suggesting that they are part of the supported function set. This is in
                            accordance with the principle that the namespace
                            <code nobreak="false">http://expath.org/ns/binary</code> is reserved solely for use in
                            QNames for functions specified in this module.</p></item></olist></div2></inform-div1><inform-div1 id="back-compatibility" diff="chg" at="A"><head>Compatibility with Previous Versions</head><p>This section summarizes the extent to which this specification is compatible with
                previous versions.</p><p>Version 4.0 of this function library is fully backwards compatible with version 1.0,
                except as noted below:</p><olist><item diff="add" at="2024-11-25"><p>The use of optional arguments in the function signatures means that minor
                        alterations to possible function calls, which would be invalid in 1.0, are
                        now supported. For example:</p><eg xml:space="preserve">bin:decode-string($string,'UTF-8',0,())</eg><p>would be invalid in 1.0, as the fourth argument <code nobreak="false">$size</code> is defined
                        to be of type <code nobreak="false">xs:integer</code>. It is valid for 4.0 as the empty
                        sequence denotes default behaviour, that is decoding all octets after
                        <code nobreak="false">$offset</code>
                    </p><p>The functions <function>bin:decode-string</function>,<function>bin:encode-string</function>,
                        <function>bin:pack-double</function>, <function>bin:pack-float</function>,
                        <function>bin:pack-integer</function>, <function>bin:pad-left</function>,
                        <function>bin:pad-right</function>, <function>bin:part</function>,
                        <function>bin:unpack-double</function>, <function>bin:unpack-float</function>,
                        <function>bin:unpack-integer</function> and <function>bin:unpack-unsigned-integer</function>
                        all have similar incompatibilities.</p></item><item><p>The use of the type <code nobreak="false">xs:unsignedByte</code> for octet arguments,
                    and of an <code nobreak="false">enum</code> type for octet order, means that invalid values
                    for these arguments will now result in a type error 
                        <xerrorref spec="XP" class="TY" code="0004"/>, rather than a dynamic
                    error with a code in the <code nobreak="false">bin</code> namespace.</p></item><item><p>The way in which <function>bin:octal</function> adjusts the supplied
                        value to a whole number of octets is now specified much more precisely, and the result
                        might differ from the interpretation adopted by existing implementations.
                        Specifically, the result might differ through the presence or absence of
                        leading zero octets.</p></item><item><p>The way in which the <function>bin:encode-string</function> and
                        <function>bin:decode-string</function> functions handle byte order, and byte order marks,
                        has been clarified. The new rules may differ from the interpretation
                        adopted by existing implementations (in particular, it differs from
                        the interpretation that was assumed by the published test suite).</p></item></olist></inform-div1></back></spec><!--XSLT Processor: Saxonica-->