and just return the
pointer to the input value.)
</para>
<para>
Finally, all variable-length types must also be passed
by reference. All variable-length types must begin
with an opaque length field of exactly 4 bytes, which will be set
by <symbol>SET_VARSIZE</symbol>; never set this field directly! All data to
be stored within that type must be located in the memory
immediately following that length field. The
length field contains the total length of the structure,
that is, it includes the size of the length field
itself.
</para>
<para>
Another important point is to avoid leaving any uninitialized bits
within data type values; for example, take care to zero out any
alignment padding bytes that might be present in structs. Without
this, logically-equivalent constants of your data type might be
seen as unequal by the planner, leading to inefficient (though not
incorrect) plans.
</para>
<warning>
<para>
<emphasis>Never</emphasis> modify the contents of a pass-by-reference input
value. If you do so you are likely to corrupt on-disk data, since
the pointer you are given might point directly into a disk buffer.
The sole exception to this rule is explained in
<xref linkend="xaggr"/>.
</para>
</warning>
<para>
As an example, we can define the type <type>text</type> as
follows:
<programlisting>
typedef struct {
int32 length;
char data[FLEXIBLE_ARRAY_MEMBER];
} text;
</programlisting>
The <literal>[FLEXIBLE_ARRAY_MEMBER]</literal> notation means that the actual
length of the data part is not specified by this declaration.
</para>
<para>
When manipulating
variable-length types, we must be careful to allocate
the correct amount of memory and set the length field correctly.
For example, if we wanted to store 40 bytes in a <structname>text</structname>
structure, we might use a code fragment like this:
<programlisting><![CDATA[
#include "postgres.h"
...
char buffer[40]; /* our source data */
...
text *destination = (text *) palloc(VARHDRSZ + 40);
SET_VARSIZE(destination, VARHDRSZ + 40);
memcpy(destination->data, buffer, 40);
...
]]>
</programlisting>
<literal>VARHDRSZ</literal> is the same as <literal>sizeof(int32)</literal>, but
it's considered good style to use the macro <literal>VARHDRSZ</literal>
to refer to the size of the overhead for a variable-length type.
Also, the length field <emphasis>must</emphasis> be set using the
<literal>SET_VARSIZE</literal> macro, not by simple assignment.
</para>
<para>
<xref linkend="xfunc-c-type-table"/> shows the C types
corresponding to many of the built-in SQL data types
of <productname>PostgreSQL</productname>.
The <quote>Defined In</quote> column gives the header file that
needs to be included to get the type definition. (The actual
definition might be in a different file that is included by the
listed file. It is recommended that users stick to the defined
interface.) Note that you should always include
<filename>postgres.h</filename> first in any source file of server
code, because it declares a number of things that you will need
anyway, and because including other headers first can cause
portability issues.
</para>
<table tocentry="1" id="xfunc-c-type-table">
<title>Equivalent C Types for Built-in SQL Types</title>
<tgroup cols="3">
<colspec colname="col1" colwidth="1*"/>
<colspec colname="col2" colwidth="1*"/>
<colspec colname="col3" colwidth="2*"/>
<thead>
<row>
<entry>
SQL Type
</entry>
<entry>
C Type
</entry>
<entry>
Defined In
</entry>
</row>
</thead>
<tbody>
<row>