  
  [1X5. Object serialisation (Pickling)[0X
  
  The  idea  of  "object  serialisation"  is  that  one  wants to store nearly
  arbitrary  [5XGAP[0X  objects  to  disk or transfer them over the network. To this
  end, one wants to convert them to a byte stream that is platform independent
  and  can  later be converted back to a copy of the same object in memory, be
  it in the same [5XGAP[0X process or another one maybe even on another machine. The
  main  problem  here  are the vast amount of different types occurring in [5XGAP[0X
  and the possibly highly self-referential structure of [5XGAP[0X objects.
  
  The  [5XIO[0X  package  contains a framework to implement object serialisation and
  implementations  for  most  of the basic data types in [5XGAP[0X. The framework is
  easily  extendible to other types and takes complete care of self-references
  and  corresponding  problems.  It  builds  upon  the  buffered I/O functions
  described in Section [14X4.[0X. We start by describing the user interface.
  
  
  [1X5.1 Result objects[0X
  
  The  following static objects are used to report about success or failure of
  the (un-)pickling operations:
  
  [1X5.1-1 IO_Error[0X
  
  [2X> IO_Error___________________________________________________[0Xglobal variable
  
  This object is returned if an error occurs.
  
  [1X5.1-2 IO_Nothing[0X
  
  [2X> IO_Nothing_________________________________________________[0Xglobal variable
  
  This  object  is returned when there is nothing to return, for example if an
  unpickler (see [2XIO_Unpickle[0X ([14X5.2-2[0X)) encounters the end of a file.
  
  [1X5.1-3 IO_OK[0X
  
  [2X> IO_OK______________________________________________________[0Xglobal variable
  
  This  object  is  returned  if  everything  went  well and there is no other
  canonical value to return to indicate this.
  
  The  only  thing  you can do with these special values is to compare them to
  each other and to other objects.
  
  
  [1X5.2 Pickling and unpickling[0X
  
  [1X5.2-1 IO_Pickle[0X
  
  [2X> IO_Pickle( [0X[3Xf, ob[0X[2X ) ______________________________________________[0Xoperation
  [6XReturns:[0X  [10XIO_OK[0X or [10XIO_Error[0X
  
  The  argument  [3Xf[0X must be an open, writable [10XFile[0X object. The object [3Xob[0X can be
  an  arbitrary [5XGAP[0X object. The operation "pickles" or "serialises" the object
  [3Xob[0X  and  writes  the result into the [10XFile[0X object [3Xf[0X. If everything is OK, the
  unique  value [10XIO_OK[0X is returned and otherwise the unique value [10XIO_Error[0X. The
  resulting  byte  stream  can  be  read again using the operation [2XIO_Unpickle[0X
  ([14X5.2-2[0X)  and  is  platform-  and  architecture  independent.  Especially the
  question  whether  a system has 32 bit or 64 bit wide words and the question
  of endianess does not matter.
  
  Note  that  not all of [5XGAP[0X's object types are supported but it is relatively
  easy  to  extend  the  system.  This  package supports in particular boolean
  values,  integers,  permutations,  rational  numbers, finite field elements,
  cyclotomics,  strings,  polynomials,  rational  functions,  lists,  records,
  compressed vectors and matrices over finite fields (objects are uncompressed
  in  the  byte  stream but recompressed during unpickling), and straight line
  programs.
  
  Self-referential  objects built from records and lists are handled correctly
  and are restored completely with the same self-references during unpickling.
  
  [1X5.2-2 IO_Unpickle[0X
  
  [2X> IO_Unpickle( [0X[3Xf[0X[2X ) ________________________________________________[0Xoperation
  [6XReturns:[0X  [10XIO_Error[0X or a [5XGAP[0X object
  
  The  argument  [3Xf[0X  must be an open, readable [10XFile[0X object. The operation reads
  from [3Xf[0X and "unpickles" the next object. If an error occurs, the unique value
  [10XIO_Error[0X  is  returned.  If  the  [10XFile[0X  object  is at end of file, the value
  [10XIO_Nothing[0X  is  returned.  Note  that  these  two  values are not picklable,
  because of their special meaning as return values of this operation here.
  
  [1X5.2-3 IO_ClearPickleCache[0X
  
  [2X> IO_ClearPickleCache( [0X[3X[0X[2X ) __________________________________________[0Xfunction
  [6XReturns:[0X  Nothing
  
  This  function  clears  the  "pickle  cache".  This  cache stores all object
  pickled  in the current recursive call to [2XIO_Pickle[0X ([14X5.2-1[0X) and is necessary
  to handle self-references. Usually it is not necessary to call this function
  explicitly.  Only  in the rare case (that should not happen) that a pickling
  or  unpickling  operation enters a break loop which is left by the user, the
  pickle  cache  has  to  be  cleared explicitly using this function for later
  calls to [2XIO_Pickle[0X ([14X5.2-1[0X) and [2XIO_Unpickle[0X ([14X5.2-2[0X) to work!
  
  
  [1X5.3 Extending the pickling framework[0X
  
  The framework can be extended for other [5XGAP[0X object types as follows:
  
  For  pickling,  a  method  for  the  operation  [2XIO_Pickle[0X  ([14X5.2-1[0X) has to be
  installed  which  does the work. If the object to be pickled has subobjects,
  then  the first action of the method is to call the function [10XIO_AddToPickled[0X
  with the object as argument. This will put it into the pickle cache and take
  care  of  self-references.  Arbitrary  subobjects  can then be pickled using
  recursive  calls  to  the  operation [2XIO_Pickle[0X ([14X5.2-1[0X) handing down the same
  [10XFile[0X  object  into  the recursion. The method must either return [10XIO_Error[0X in
  case  of  an  error  or  [10XIO_OK[0X  if everything goes well. Before returning, a
  method   that   has   called   [10XIO_AddToPickled[0X   must   call   the  function
  [10XIO_FinalizePickled[0X  without  arguments [13Xunder all circumstances[0X. If this call
  is missing, global data for the pickling procedure becomes corrupt!
  
  Every  pickling method must first write a 4 byte magic value such that later
  during  unpickling  of  the  byte  stream the right unpickling method can be
  called  (see  below).  Then  it can write arbitrary data, however, this data
  should be platform- and architecture independent, and it must be possible to
  unpickle it later without "lookahead".
  
  Pickling  methods  should  usually  not  go into a break loop, because after
  leaving the user has to call [2XIO_ClearPickleCache[0X ([14X5.2-3[0X) explicitly!
  
  Unpickling  is  implemented  as  follows: For every 4 byte magic value there
  must  be  a function bound to that value in the record [10XIO_Unpicklers[0X. If the
  unpickling  operation  [2XIO_Unpickle[0X  ([14X5.2-2[0X)  encounters that magic value, it
  calls  the  corresponding  unpickling  function. This function just gets one
  [10XFile[0X  object  as  argument.  Since  the  magic value is already read, it can
  immediately  start  with  reading  and  rebuilding  the serialised object in
  memory. The method has to take care to restore the object including its type
  completely.
  
  If  an  object  type  has  subobjects,  the unpickling function has to first
  create   a  skeleton  of  the  object  without  its  subobjects,  then  call
  [10XIO_AddToUnpickled[0X  on this skeleton, [13Xbefore[0X unpickling subobjects. If things
  are  not  done  in  this  order, the handling of self-references down in the
  recursion   will   not   work!   An  unpickling  function  that  has  called
  [10XIO_AddToUnpickled[0X  at the beginning has to call [10XIO_FinalizeUnpickled[0X without
  arguments before returning [13Xunder all circumstances[0X! If this call is missing,
  global data for the unpickling procedure becomes corrupt!
  
  Of  course, unpickling functions can recursively call [2XIO_Unpickle[0X ([14X5.2-2[0X) to
  unpickle subobjects. Apart from this, unpickling functions can use arbitrary
  reading  functions  on  the  [10XFile[0X  object.  However,  they  should only read
  sequentially  and never move the current file position pointer otherwise. An
  unpickling  function  should  return  the  newly created object or the value
  [10XIO_Error[0X  if  an  error  occurred.  They  should never go into a break loop,
  because  after  leaving  the  user  has  to call [2XIO_ClearPickleCache[0X ([14X5.2-3[0X)
  explicitly!
  
  Perhaps  the  best  way to learn how to extend the framework is to study the
  code for the basic [5XGAP[0X objects in the file [11Xpkg/io/gap/pickle.gi[0X.
  
