(root)/
libredwg-0.13/
src/
free.c
       1  /*****************************************************************************/
       2  /*  LibreDWG - free implementation of the DWG file format                    */
       3  /*                                                                           */
       4  /*  Copyright (C) 2018-2023 Free Software Foundation, Inc.                   */
       5  /*                                                                           */
       6  /*  This library is free software, licensed under the terms of the GNU       */
       7  /*  General Public License as published by the Free Software Foundation,     */
       8  /*  either version 3 of the License, or (at your option) any later version.  */
       9  /*  You should have received a copy of the GNU General Public License        */
      10  /*  along with this program.  If not, see <http://www.gnu.org/licenses/>.    */
      11  /*****************************************************************************/
      12  
      13  /*
      14   * free.c: helper functions to free all spec fields
      15   * written by Reini Urban
      16   * modified by Denis Pruchkovsky
      17   */
      18  
      19  #include "config.h"
      20  #ifdef __STDC_ALLOC_LIB__
      21  #  define __STDC_WANT_LIB_EXT2__ 1 /* for strdup */
      22  #else
      23  #  define _USE_BSD 1
      24  #endif
      25  #include <stdio.h>
      26  #include <stdlib.h>
      27  #include <string.h>
      28  #include <assert.h>
      29  
      30  #include "common.h"
      31  #include "bits.h"
      32  #include "dwg.h"
      33  #include "decode.h"
      34  #include "free.h"
      35  #include "classes.h"
      36  #include "hash.h"
      37  #include "free.h"
      38  
      39  static unsigned int loglevel;
      40  #ifdef USE_TRACING
      41  static int env_var_checked_p;
      42  #endif
      43  #define DWG_LOGLEVEL loglevel
      44  #include "logging.h"
      45  
      46  /* the current version per spec block */
      47  static unsigned int cur_ver = 0;
      48  static Bit_Chain pdat = { 0 };
      49  static BITCODE_BL rcount1, rcount2;
      50  
      51  /*--------------------------------------------------------------------------------
      52   * MACROS
      53   */
      54  
      55  #define ACTION free
      56  #define IS_FREE
      57  
      58  #define FREE_IF(ptr)                                                          \
      59    {                                                                           \
      60      if (ptr)                                                                  \
      61        free (ptr);                                                             \
      62      ptr = NULL;                                                               \
      63    }
      64  
      65  #undef UNTIL
      66  #undef SINCE
      67  #undef PRE
      68  #undef VERSIONS
      69  #undef VERSION
      70  #define UNTIL(v) if (dat->from_version <= v)
      71  #define SINCE(v) if (dat->from_version >= v)
      72  #define PRE(v) if (dat->from_version < v)
      73  #define VERSIONS(v1, v2)                                                      \
      74    if (dat->from_version >= v1 && dat->from_version <= v2)
      75  #define VERSION(v) if (dat->from_version == v)
      76  
      77  #define VALUE(value, type, dxf)
      78  #define VALUE_RC(value, dxf) VALUE (value, RC, dxf)
      79  #define VALUE_RS(value, dxf) VALUE (value, RS, dxf)
      80  #define VALUE_RL(value, dxf) VALUE (value, RL, dxf)
      81  #define VALUE_RLx(value, dxf) VALUE (value, RL, dxf)
      82  #define VALUE_RD(value, dxf) VALUE (value, RD, dxf)
      83  #define VALUE_BD(value, dxf) VALUE (value, BD, dxf)
      84  
      85  #define FIELD(name, type)                                                     \
      86    {                                                                           \
      87    }
      88  #define FIELD_TRACE(name, type)                                               \
      89    LOG_TRACE (#name ": " FORMAT_##type "\n", _obj->name)
      90  #define FIELD_G_TRACE(name, type, dxfgroup)                                   \
      91    LOG_TRACE (#name ": " FORMAT_##type " [" #type " %d]\n", _obj->name,        \
      92               dxfgroup)
      93  #define FIELD_CAST(name, type, cast, dxf)                                     \
      94    {                                                                           \
      95    }
      96  #define SUB_FIELD_CAST(o, name, type, cast, dxf)                              \
      97    {                                                                           \
      98    }
      99  #define FIELD_VALUE(name) _obj->name
     100  #define SUB_FIELD(o, nam, type, dxf) FIELD (_obj->o.nam, type)
     101  
     102  #define ANYCODE -1
     103  #define FIELD_HANDLE(nam, code, dxf) VALUE_HANDLE (_obj->nam, nam, code, dxf)
     104  #define SUB_FIELD_HANDLE(o, nam, code, dxf)                                   \
     105    if (obj->fixedtype == DWG_TYPE_TABLESTYLE)                                  \
     106      LOG_HANDLE ("free TABLESTYLE.%s.%s\n", #o, #nam);                         \
     107    VALUE_HANDLE (_obj->o.nam, nam, code, dxf)
     108  // compare to dwg_decode_handleref_with_code: not all refs are stored in the
     109  // object_ref vector, like relative ptrs and NULL.
     110  // But with INDXF skip the NULL HDL, it is global and shared there.
     111  // obj is the relative base object here and there.
     112  #define VALUE_HANDLE(ref, nam, _code, dxf)                                    \
     113    if (ref && !ref->handleref.is_global)                                       \
     114      {                                                                         \
     115        free (ref);                                                             \
     116        ref = NULL;                                                             \
     117      } /* else freed globally */
     118  #define FIELD_DATAHANDLE(name, code, dxf) FIELD_HANDLE (name, code, dxf)
     119  #define FIELD_HANDLE_N(name, vcount, code, dxf) FIELD_HANDLE (name, code, dxf)
     120  #define FIELD_VECTOR_INL(nam, type, size, dxf)
     121  #define VALUE_H(hdl, dxf)
     122  
     123  #define FIELD_B(name, dxf) FIELD (name, B)
     124  #define FIELD_BB(name, dxf) FIELD (name, BB)
     125  #define FIELD_3B(name, dxf) FIELD (name, 3B)
     126  #define FIELD_BS(name, dxf) FIELD (name, BS)
     127  #define FIELD_BL(name, dxf) FIELD (name, BL)
     128  #define FIELD_BLL(name, dxf) FIELD (name, BLL)
     129  #define FIELD_BD(name, dxf) FIELD (name, BD)
     130  #define FIELD_RC(name, dxf) FIELD (name, RC)
     131  #define FIELD_RS(name, dxf) FIELD (name, RS)
     132  #define FIELD_RD(name, dxf) FIELD (name, RD)
     133  #define FIELD_RL(name, dxf) FIELD (name, RL)
     134  #define FIELD_RLL(name, dxf) FIELD (name, RLL)
     135  #define FIELD_MC(name, dxf) FIELD (name, MC)
     136  #define FIELD_MS(name, dxf) FIELD (name, MS)
     137  #define FIELD_TV(name, dxf) FREE_IF (FIELD_VALUE (name))
     138  #define VALUE_TV(value, dxf) FREE_IF (value)
     139  #define VALUE_TF(value, dxf) FREE_IF (value)
     140  #define VALUE_TFF(value, dxf)
     141  #define FIELD_TU(name, dxf) FIELD_TV (name, dxf)
     142  #define FIELD_TF(name, len, dxf) FIELD_TV (name, dxf)
     143  #define FIELD_TFv(name, len, dxf) FIELD_TV (name, dxf)
     144  #define FIELD_TFF(name, len, dxf)                                             \
     145    {                                                                           \
     146    }
     147  #define FIELD_T(name, dxf) FIELD_TV (name, dxf)
     148  #define FIELD_BINARY(name, len, dxf) FIELD_TV (name, dxf)
     149  #define FIELD_T16(name, dxf) FIELD_TV (name, dxf)
     150  #define FIELD_TU16(name, dxf) FIELD_TV (name, dxf)
     151  #define FIELD_T32(name, dxf) FIELD_TV (name, dxf)
     152  #define FIELD_BT(name, dxf) FIELD (name, BT);
     153  #define FIELD_4BITS(name, dxf)                                                \
     154    {                                                                           \
     155    }
     156  #define FIELD_BE(name, dxf)                                                   \
     157    {                                                                           \
     158    }
     159  #define FIELD_DD(name, _default, dxf)                                         \
     160    {                                                                           \
     161    }
     162  #define FIELD_2DD(name, def, dxf)                                             \
     163    {                                                                           \
     164    }
     165  #define FIELD_3DD(name, def, dxf)                                             \
     166    {                                                                           \
     167    }
     168  #define FIELD_2RD(name, dxf)                                                  \
     169    {                                                                           \
     170    }
     171  #define FIELD_2BD(name, dxf)                                                  \
     172    {                                                                           \
     173    }
     174  #define FIELD_2BD_1(name, dxf)                                                \
     175    {                                                                           \
     176    }
     177  #define FIELD_3RD(name, dxf)                                                  \
     178    {                                                                           \
     179    }
     180  #define FIELD_3BD(name, dxf)                                                  \
     181    {                                                                           \
     182    }
     183  #define FIELD_3BD_1(name, dxf)                                                \
     184    {                                                                           \
     185    }
     186  #define FIELD_3DPOINT(name, dxf)                                              \
     187    {                                                                           \
     188    }
     189  #define FIELD_2PT_TRACE(name, type, dxf)                                      \
     190    {                                                                           \
     191    }
     192  #define FIELD_3PT_TRACE(name, type, dxf)                                      \
     193    {                                                                           \
     194    }
     195  #define FIELD_TIMEBLL(name, dxf)
     196  #define FIELD_TIMERLL(name, dxf)
     197  #define FIELD_CMC(color, dxf)                                                 \
     198    SINCE (R_2004)                                                              \
     199    {                                                                           \
     200      FIELD_T (color.name, 0);                                                  \
     201      FIELD_T (color.book_name, 0);                                             \
     202    }
     203  #define SUB_FIELD_CMC(o, color, dxf)                                          \
     204    SINCE (R_2004)                                                              \
     205    {                                                                           \
     206      VALUE_TV (_obj->o.color.name, 0);                                         \
     207      VALUE_TV (_obj->o.color.book_name, 0);                                    \
     208    }
     209  
     210  // FIELD_VECTOR_N(name, type, size):
     211  // reads data of the type indicated by 'type' 'size' times and stores
     212  // it all in the vector called 'name'.
     213  #define FIELD_VECTOR_N(nam, type, size, dxf)                                  \
     214    if ((size) && _obj->nam)                                                    \
     215      {                                                                         \
     216        for (vcount = 0; vcount < (BITCODE_BL)(size); vcount++)                 \
     217          FIELD_##type (nam[vcount], dxf);                                      \
     218      }                                                                         \
     219    FIELD_TV (nam, dxf);
     220  #define FIELD_VECTOR_T(name, type, size, dxf)                                 \
     221    FIELD_VECTOR_N (name, TV, _obj->size, dxf)
     222  #define FIELD_VECTOR(name, type, size, dxf)                                   \
     223    FIELD_VECTOR_N (name, type, _obj->size, dxf)
     224  #define FIELD_2RD_VECTOR(name, size, dxf) FIELD_TV (name, dxf)
     225  #define FIELD_2DD_VECTOR(name, size, dxf) FIELD_TV (name, dxf)
     226  #define FIELD_3DPOINT_VECTOR(name, size, dxf) FIELD_TV (name, dxf)
     227  #define HANDLE_VECTOR_N(name, size, code, dxf)                                \
     228    if (_obj->name)                                                             \
     229      {                                                                         \
     230        for (vcount = 0; vcount < (BITCODE_BL)size; vcount++)                   \
     231          {                                                                     \
     232            FIELD_HANDLE_N (name[vcount], vcount, code, dxf);                   \
     233          }                                                                     \
     234        FIELD_TV (name, dxf)                                                    \
     235      }
     236  #define HANDLE_VECTOR(name, sizefield, code, dxf)                             \
     237    HANDLE_VECTOR_N (name, FIELD_VALUE (sizefield), code, dxf)
     238  #define SUB_HANDLE_VECTOR(o, name, sizefield, code, dxf)                      \
     239    if (_obj->o.name && _obj->o.sizefield)                                      \
     240      {                                                                         \
     241        for (vcount = 0; vcount < (BITCODE_BL)_obj->o.sizefield; vcount++)      \
     242          {                                                                     \
     243            SUB_FIELD_HANDLE (o, name[vcount], code, dxf);                      \
     244          }                                                                     \
     245        FREE_IF (_obj->o.name)                                                  \
     246      }
     247  #define SUB_FIELD_VECTOR(o, nam, type, sizefield, dxf)                        \
     248    if (_obj->o.sizefield && _obj->o.nam)                                       \
     249      {                                                                         \
     250        for (vcount = 0; vcount < (BITCODE_BL)(_obj->o.sizefield); vcount++)    \
     251          SUB_FIELD_##type (o, nam[vcount], dxf);                               \
     252      }                                                                         \
     253    FREE_IF (_obj->o.nam)
     254  
     255  #define FIELD_NUM_INSERTS(num_inserts, type, dxf)
     256  #define FIELD_XDATA(name, size) dwg_free_xdata (_obj, _obj->size)
     257  
     258  #define REACTORS(code)                                                        \
     259    if (obj->tio.object->reactors)                                              \
     260      {                                                                         \
     261        for (vcount = 0; vcount < obj->tio.object->num_reactors; vcount++)      \
     262          VALUE_HANDLE (obj->tio.object->reactors[vcount], reactors, code,      \
     263                        330);                                                   \
     264        VALUE_TV (obj->tio.object->reactors, 0);                                \
     265      }
     266  #define ENT_REACTORS(code)                                                    \
     267    if (_ent->reactors)                                                         \
     268      {                                                                         \
     269        for (vcount = 0; vcount < _ent->num_reactors; vcount++)                 \
     270          VALUE_HANDLE (_ent->reactors[vcount], reactors, code, 330);           \
     271        VALUE_TV (_ent->reactors, 0);                                           \
     272      }
     273  #define XDICOBJHANDLE(code)                                                   \
     274    SINCE (R_2004)                                                              \
     275    {                                                                           \
     276      if (!obj->tio.object->is_xdic_missing)                                    \
     277        {                                                                       \
     278          VALUE_HANDLE (obj->tio.object->xdicobjhandle, xdicobjhandle, code,    \
     279                        0);                                                     \
     280        }                                                                       \
     281    }                                                                           \
     282    PRIOR_VERSIONS                                                              \
     283    {                                                                           \
     284      VALUE_HANDLE (obj->tio.object->xdicobjhandle, xdicobjhandle, code, 0);    \
     285    }
     286  #define ENT_XDICOBJHANDLE(code)                                               \
     287    SINCE (R_2004)                                                              \
     288    {                                                                           \
     289      if (!_ent->is_xdic_missing)                                               \
     290        {                                                                       \
     291          VALUE_HANDLE (_ent->xdicobjhandle, xdicobjhandle, code, 0);           \
     292        }                                                                       \
     293    }                                                                           \
     294    PRIOR_VERSIONS                                                              \
     295    {                                                                           \
     296      VALUE_HANDLE (_ent->xdicobjhandle, xdicobjhandle, code, 0);               \
     297    }
     298  
     299  #define END_REPEAT(field) FIELD_TV (field, 0)
     300  
     301  #define COMMON_ENTITY_HANDLE_DATA
     302  #define SECTION_STRING_STREAM
     303  #define START_STRING_STREAM
     304  #define END_STRING_STREAM
     305  #define START_HANDLE_STREAM
     306  
     307  #include "spec.h"
     308  
     309  #define DWG_ENTITY(token)                                                     \
     310    static int dwg_free_##token##_private (Bit_Chain *dat, Bit_Chain *hdl_dat,  \
     311                                           Bit_Chain *str_dat,                  \
     312                                           Dwg_Object *restrict obj);           \
     313                                                                                \
     314    static int dwg_free_##token (Bit_Chain *restrict dat,                       \
     315                                 Dwg_Object *restrict obj)                      \
     316    {                                                                           \
     317      int error = 0;                                                            \
     318      if (obj->tio.entity)                                                      \
     319        {                                                                       \
     320          LOG_HANDLE ("Free entity " #token " [%d]\n", obj->index)              \
     321          if (obj->tio.entity->tio.token)                                       \
     322            error = dwg_free_##token##_private (dat, dat, dat, obj);            \
     323                                                                                \
     324          dwg_free_common_entity_data (obj);                                    \
     325          dwg_free_eed (obj);                                                   \
     326          if (obj->tio.entity)                                                  \
     327            {                                                                   \
     328              FREE_IF (obj->tio.entity->tio.token);                             \
     329              FREE_IF (obj->tio.entity);                                        \
     330            }                                                                   \
     331        }                                                                       \
     332      obj->parent = NULL;                                                       \
     333      return error;                                                             \
     334    }                                                                           \
     335    static int dwg_free_##token##_private (Bit_Chain *dat, Bit_Chain *hdl_dat,  \
     336                                           Bit_Chain *str_dat,                  \
     337                                           Dwg_Object *restrict obj)            \
     338    {                                                                           \
     339      BITCODE_BL vcount, rcount3, rcount4;                                      \
     340      Dwg_Entity_##token *ent, *_obj;                                           \
     341      Dwg_Object_Entity *_ent;                                                  \
     342      Dwg_Data *dwg = obj->parent;                                              \
     343      int error = 0;                                                            \
     344      _ent = obj->tio.entity;                                                   \
     345      if (!_ent)                                                                \
     346        return 0;                                                               \
     347      _obj = ent = _ent->tio.token;
     348  
     349  #define DWG_ENTITY_END                                                        \
     350      FREE_IF (obj->unknown_rest);                                              \
     351    return error;                                                               \
     352    }
     353  
     354  #define DWG_OBJECT(token)                                                     \
     355    static int dwg_free_##token##_private (Bit_Chain *dat, Bit_Chain *hdl_dat,  \
     356                                           Bit_Chain *str_dat,                  \
     357                                           Dwg_Object *restrict obj);           \
     358                                                                                \
     359    static int dwg_free_##token (Bit_Chain *restrict dat,                       \
     360                                 Dwg_Object *restrict obj)                      \
     361    {                                                                           \
     362      int error = 0;                                                            \
     363      Dwg_Object_##token *_obj = NULL;                                          \
     364      if (obj->tio.object)                                                      \
     365        {                                                                       \
     366          _obj = obj->tio.object->tio.token;                                    \
     367          LOG_HANDLE ("Free object " #token " [%d]\n", obj->index)              \
     368          error = dwg_free_##token##_private (dat, dat, dat, obj);              \
     369          dwg_free_common_object_data (obj);                                    \
     370          dwg_free_eed (obj);                                                   \
     371          FREE_IF (_obj);                                                       \
     372          FREE_IF (obj->tio.object);                                            \
     373        }                                                                       \
     374      obj->parent = NULL;                                                       \
     375      return error;                                                             \
     376    }                                                                           \
     377                                                                                \
     378    static int dwg_free_##token##_private (Bit_Chain *dat, Bit_Chain *hdl_dat,  \
     379                                           Bit_Chain *str_dat,                  \
     380                                           Dwg_Object *restrict obj)            \
     381    {                                                                           \
     382      BITCODE_BL vcount, rcount3, rcount4;                                      \
     383      Dwg_Object_##token *_obj;                                                 \
     384      Dwg_Data *dwg = obj->parent;                                              \
     385      int error = 0;                                                            \
     386      if (!obj->tio.object)                                                     \
     387        return 0;                                                               \
     388      _obj = obj->tio.object->tio.token;
     389  
     390  /* obj itself is allocated via dwg->object[], dxfname is klass->dxfname or
     391   * static */
     392  #define DWG_OBJECT_END                                                        \
     393      FREE_IF (obj->unknown_rest);                                              \
     394    return error;                                                               \
     395    }
     396  
     397  static void
     398  dwg_free_common_entity_data (Dwg_Object *obj)
     399  {
     400  
     401    Dwg_Data *dwg = obj->parent;
     402    Bit_Chain *dat = &pdat;
     403    Bit_Chain *hdl_dat = &pdat;
     404    Dwg_Object_Entity *_obj;
     405    Dwg_Object_Entity *_ent;
     406    BITCODE_BL vcount;
     407    int error = 0;
     408  
     409    _ent = obj->tio.entity;
     410    if (!_ent)
     411      return;
     412    _obj = _ent;
     413  
     414    FREE_IF (_ent->preview);
     415  
     416  // clang-format off
     417    #include "common_entity_data.spec"
     418    if (dat->from_version >= R_2007 && _ent->color.flag & 0x40)
     419      FIELD_HANDLE (color.handle, 0, 430);
     420    SINCE (R_13b1) {
     421      #include "common_entity_handle_data.spec"
     422    }
     423    // clang-format on
     424  }
     425  
     426  static void
     427  dwg_free_common_object_data (Dwg_Object *obj)
     428  {
     429  
     430    Dwg_Data *dwg = obj->parent;
     431    Bit_Chain *dat = &pdat;
     432    Bit_Chain *hdl_dat = &pdat;
     433    Dwg_Object_Object *_obj = obj->tio.object;
     434    BITCODE_BL vcount;
     435    int error = 0;
     436  
     437  // clang-format off
     438    #include "common_object_handle_data.spec"
     439    // clang-format on
     440  }
     441  
     442  static void
     443  dwg_free_xdata (Dwg_Object_XRECORD *obj, int size)
     444  {
     445    dwg_free_xdata_resbuf (obj->xdata);
     446    obj->xdata = NULL;
     447  }
     448  
     449  EXPORT void
     450  dwg_free_eed (Dwg_Object *obj)
     451  {
     452    BITCODE_BL i;
     453    if (obj->supertype == DWG_SUPERTYPE_ENTITY)
     454      {
     455        Dwg_Object_Entity *_obj = obj->tio.entity;
     456        for (i = 0; i < _obj->num_eed; i++)
     457          {
     458            FREE_IF (_obj->eed[i].raw);
     459            FREE_IF (_obj->eed[i].data);
     460          }
     461        FREE_IF (_obj->eed);
     462        _obj->num_eed = 0;
     463      }
     464    else
     465      {
     466        Dwg_Object_Object *_obj = obj->tio.object;
     467        if (!_obj || !_obj->eed)
     468          return;
     469        for (i = 0; i < _obj->num_eed; i++)
     470          {
     471            FREE_IF (_obj->eed[i].raw);
     472            FREE_IF (_obj->eed[i].data);
     473          }
     474        FREE_IF (_obj->eed);
     475        _obj->num_eed = 0;
     476      }
     477  }
     478  
     479  #include "dwg.spec"
     480  
     481  // could be a hash or switch, but there are not that many DEBUGGING classes.
     482  // but a switch is fine, as we get all missing types in objects.inc, generated
     483  // by regen-dynapi
     484  int
     485  dwg_free_variable_no_class (Dwg_Data *restrict dwg, Dwg_Object *restrict obj)
     486  {
     487    Bit_Chain *dat = &pdat;
     488  
     489  #undef DWG_ENTITY
     490  #undef DWG_OBJECT
     491  #define FREE_NOCLASS(name)                                                    \
     492    case DWG_TYPE_##name:                                                       \
     493      return dwg_free_##name (dat, obj);
     494  #define DWG_ENTITY(name) FREE_NOCLASS (name)
     495  #define DWG_OBJECT(name) FREE_NOCLASS (name)
     496  
     497    switch (obj->fixedtype)
     498      {
     499  #include "objects.inc"
     500  
     501      case DWG_TYPE_FREED:
     502        break; // already freed
     503  
     504      case DWG_TYPE_ACDSRECORD:
     505      case DWG_TYPE_ACDSSCHEMA:
     506      case DWG_TYPE_NPOCOLLECTION:
     507      case DWG_TYPE_XREFPANELOBJECT:
     508      default:
     509        LOG_ERROR ("Unhandled class %s, fixedtype %d in objects.inc",
     510                   dwg_type_name (obj->fixedtype), (int)obj->fixedtype);
     511      }
     512  
     513  #undef DWG_ENTITY
     514  #undef DWG_OBJECT
     515  #undef FREE_NOCLASS
     516  
     517    return DWG_ERR_UNHANDLEDCLASS;
     518  }
     519  
     520  /* returns error.
     521   */
     522  int
     523  dwg_free_variable_type (Dwg_Data *restrict dwg, Dwg_Object *restrict obj)
     524  {
     525    const int i = obj->type - 500;
     526    Dwg_Class *klass;
     527    Bit_Chain *dat = &pdat;
     528  
     529    // no matching class
     530    if (i < 0 || i >= (int)dwg->num_classes)
     531      {
     532        LOG_WARN ("No class for %s type %d found", obj->name, obj->type);
     533        return dwg_free_variable_no_class (dwg, obj);
     534      }
     535  
     536    klass = &dwg->dwg_class[i];
     537    if (!klass || !klass->dxfname || !obj->dxfname)
     538      {
     539        LOG_WARN ("No class for %s type %d found", obj->name, obj->type);
     540        return dwg_free_variable_no_class (dwg, obj);
     541      }
     542  
     543    if (strNE (obj->dxfname, klass->dxfname))
     544      {
     545        // But we know how to handle the UNKNOWN_* types
     546        if (obj->fixedtype == DWG_TYPE_UNKNOWN_OBJ
     547            || obj->fixedtype == DWG_TYPE_UNKNOWN_ENT)
     548          return DWG_ERR_UNHANDLEDCLASS;
     549        else
     550          {
     551            LOG_ERROR ("Wrong %s.type %d for obj [%d]: != %s", obj->dxfname,
     552                       obj->type, obj->index, klass->dxfname);
     553            return dwg_free_variable_no_class (dwg, obj);
     554          }
     555      }
     556  
     557      // global class dispatcher:
     558      // with indxf even DEBUGGING objects, such as TABLE are created.
     559      // usually not written/encoded though.
     560  
     561      // clang-format off
     562    #include "classes.inc"
     563  
     564    #undef WARN_UNHANDLED_CLASS
     565    #undef WARN_UNSTABLE_CLASS
     566    // clang-format on
     567  
     568    LOG_WARN ("No class for %s type %d found", obj->name, obj->type);
     569    return dwg_free_variable_no_class (dwg, obj);
     570  }
     571  
     572  /* returns error */
     573  int
     574  dwg_free_variable_type_private (Dwg_Object *restrict obj)
     575  {
     576    Dwg_Data *restrict dwg = obj->parent;
     577    Bit_Chain *dat = &pdat;
     578  
     579  #undef DWG_ENTITY
     580  #undef DWG_OBJECT
     581  #define FREE_NOCLASS(name)                                                    \
     582    case DWG_TYPE_##name:                                                       \
     583      return dwg_free_##name##_private (dat, dat, dat, obj);
     584  #define DWG_ENTITY(name) FREE_NOCLASS (name)
     585  #define DWG_OBJECT(name) FREE_NOCLASS (name)
     586  
     587    switch (obj->fixedtype)
     588      {
     589  #include "objects.inc"
     590  
     591      case DWG_TYPE_FREED:
     592        break; // already freed
     593  
     594      case DWG_TYPE_ACDSRECORD:
     595      case DWG_TYPE_ACDSSCHEMA:
     596      case DWG_TYPE_NPOCOLLECTION:
     597      case DWG_TYPE_XREFPANELOBJECT:
     598      default:
     599        LOG_ERROR ("Unhandled class %s, fixedtype %d in objects.inc",
     600                   dwg_type_name (obj->fixedtype), (int)obj->fixedtype);
     601      }
     602  
     603  #undef DWG_ENTITY
     604  #undef DWG_OBJECT
     605  #undef FREE_NOCLASS
     606  
     607    return DWG_ERR_UNHANDLEDCLASS;
     608  }
     609  
     610  // after downconvert_TABLESTYLE()
     611  // we need to pass through the old code, as the new code is handled in the spec
     612  // free() following from_version, not version.
     613  static void
     614  free_TABLESTYLE_r2010 (Bit_Chain *restrict dat, Dwg_Object *restrict obj)
     615  {
     616    Dwg_Object_TABLESTYLE *_obj
     617        = obj->tio.object ? obj->tio.object->tio.TABLESTYLE : NULL;
     618    if (!obj || obj->fixedtype != DWG_TYPE_TABLESTYLE)
     619      {
     620        LOG_ERROR ("Invalid fixedtype %u for free_TABLESTYLE_r2010",
     621                   obj ? obj->fixedtype : 0);
     622        return;
     623      }
     624    LOG_HANDLE ("free_TABLESTYLE_r2010\n");
     625    if (_obj->rowstyles)
     626      for (unsigned i = 0; i < 3; i++)
     627        {
     628          for (unsigned j = 0; j < 6; j++)
     629            {
     630              SUB_FIELD_CMTC (rowstyles[i].borders[j], color, 0);
     631            }
     632          FREE_IF (_obj->rowstyles[i].borders);
     633          SUB_FIELD_HANDLE (rowstyles[i], text_style, 5, 7);
     634          SUB_FIELD_CMTC (rowstyles[i], text_color, 0);
     635          SUB_FIELD_CMTC (rowstyles[i], fill_color, 0);
     636        }
     637    FREE_IF (_obj->rowstyles);
     638    _obj->num_rowstyles = 0;
     639    for (unsigned j = 0; j < _obj->sty.cellstyle.num_borders; j++)
     640      {
     641        SUB_FIELD_HANDLE (sty.cellstyle.borders[j], ltype, 3, 340);
     642        SUB_FIELD_CMTC (sty.cellstyle.borders[j], color, 0);
     643      }
     644    FIELD_CMTC (sty.cellstyle.bg_color, 62);
     645    FIELD_T (sty.cellstyle.content_format.value_format_string, 300);
     646    if (_obj->numoverrides)
     647      {
     648        for (unsigned j = 0; j < _obj->ovr.cellstyle.num_borders; j++)
     649          {
     650            SUB_FIELD_HANDLE (ovr.cellstyle.borders[j], ltype, 3, 340);
     651            SUB_FIELD_CMTC (ovr.cellstyle.borders[j], color, 0);
     652          }
     653        FIELD_CMTC (ovr.cellstyle.bg_color, 62);
     654        FIELD_T (ovr.cellstyle.content_format.value_format_string, 300);
     655      }
     656    FIELD_TV (name, 3);
     657    FIELD_TV (sty.name, 300);
     658    FIELD_TV (ovr.name, 300);
     659  }
     660  
     661  static void
     662  free_preR13_object (Dwg_Object *obj)
     663  {
     664    int error = 0;
     665    long unsigned int j;
     666    Dwg_Data *dwg;
     667    Bit_Chain *dat = &pdat;
     668  
     669    // if (obj->name)
     670    //   LOG_HANDLE ("free_preR13_object: %s %d\n", obj->name, obj->index)
     671    if (obj && obj->parent)
     672      {
     673        dwg = obj->parent;
     674        dat->version = dwg->header.version;
     675        dat->from_version = dwg->header.from_version;
     676      }
     677    else
     678      return;
     679    if (obj->type == DWG_TYPE_FREED || obj->tio.object == NULL)
     680      return;
     681  
     682    if (obj->supertype == DWG_SUPERTYPE_ENTITY)
     683      {
     684        Dwg_Object_Entity *_obj = obj->tio.entity;
     685        FIELD_HANDLE (layer, 2, 8);
     686        if (_obj->flag_r11 & FLAG_R11_HAS_LTYPE) // 2
     687          FIELD_HANDLE (ltype, 1, 6);
     688        if (_obj->flag_r11 & FLAG_R11_HAS_HANDLING)
     689          {   // 32
     690            ; // obj->handle is static
     691          }
     692      }
     693  
     694    if (obj->fixedtype == DWG_TYPE_UNUSED // deleted
     695        && dwg->header.version < R_2_0b && obj->type > 64)
     696      {
     697        obj->type = -(int8_t)obj->type;
     698        // handle only entities with extra vectors specially
     699        switch (obj->type)
     700          {
     701          case DWG_TYPE_TEXT_r11:
     702            dwg_free_TEXT (dat, obj);
     703            break;
     704          case DWG_TYPE_ATTRIB_r11:
     705            dwg_free_ATTRIB (dat, obj);
     706            break;
     707          case DWG_TYPE_ATTDEF_r11:
     708            dwg_free_ATTDEF (dat, obj);
     709            break;
     710          case DWG_TYPE_BLOCK_r11:
     711            dwg_free_BLOCK (dat, obj);
     712            break;
     713          case DWG_TYPE_INSERT_r11:
     714            dwg_free_INSERT (dat, obj);
     715            break;
     716          case DWG_TYPE_DIMENSION_r11:
     717            switch (obj->tio.entity->flag_r11)
     718              {
     719              case 64:
     720                dwg_free_DIMENSION_LINEAR (dat, obj);
     721                break;
     722              case 65:
     723                dwg_free_DIMENSION_ALIGNED (dat, obj);
     724                break;
     725              case 66:
     726                dwg_free_DIMENSION_ANG2LN (dat, obj);
     727                break;
     728              case 68:
     729                dwg_free_DIMENSION_DIAMETER (dat, obj);
     730                break;
     731              case 72:
     732                dwg_free_DIMENSION_RADIUS (dat, obj);
     733                break;
     734              case 80:
     735                dwg_free_DIMENSION_ANG3PT (dat, obj);
     736                break;
     737              case 96:
     738                dwg_free_DIMENSION_ORDINATE (dat, obj);
     739                break;
     740              default:
     741                LOG_ERROR ("Unknown preR11 %s.flag_r11 %d", obj->name,
     742                           obj->tio.entity->flag_r11)
     743              }
     744            break;
     745          // now the rest
     746          default:
     747            dwg_free_POINT (dat, obj);
     748            break;
     749          }
     750      }
     751  
     752    // we could also use (Dwg_Object_Type_r11)obj->type
     753    switch (obj->fixedtype)
     754      {
     755      case DWG_TYPE_TEXT:
     756        dwg_free_TEXT (dat, obj);
     757        break;
     758      case DWG_TYPE_ATTRIB:
     759        dwg_free_ATTRIB (dat, obj);
     760        break;
     761      case DWG_TYPE_ATTDEF:
     762        dwg_free_ATTDEF (dat, obj);
     763        break;
     764      case DWG_TYPE_BLOCK:
     765        dwg_free_BLOCK (dat, obj);
     766        break;
     767      case DWG_TYPE_ENDBLK:
     768        dwg_free_ENDBLK (dat, obj);
     769        break;
     770      case DWG_TYPE_SEQEND:
     771        dwg_free_SEQEND (dat, obj);
     772        break;
     773      case DWG_TYPE_REPEAT:
     774        dwg_free_REPEAT (dat, obj);
     775        break;
     776      case DWG_TYPE_ENDREP:
     777        dwg_free_ENDREP (dat, obj);
     778        break;
     779      case DWG_TYPE_INSERT:
     780        dwg_free_INSERT (dat, obj);
     781        break;
     782      case DWG_TYPE_VERTEX_2D:
     783        dwg_free_VERTEX_2D (dat, obj);
     784        break;
     785      case DWG_TYPE_VERTEX_3D:
     786        dwg_free_VERTEX_3D (dat, obj);
     787        break;
     788      case DWG_TYPE_VERTEX_MESH:
     789        dwg_free_VERTEX_MESH (dat, obj);
     790        break;
     791      case DWG_TYPE_VERTEX_PFACE:
     792        dwg_free_VERTEX_PFACE (dat, obj);
     793        break;
     794      case DWG_TYPE_VERTEX_PFACE_FACE:
     795        dwg_free_VERTEX_PFACE_FACE (dat, obj);
     796        break;
     797      case DWG_TYPE_POLYLINE_2D:
     798        dwg_free_POLYLINE_2D (dat, obj);
     799        break;
     800      case DWG_TYPE_POLYLINE_3D:
     801        dwg_free_POLYLINE_3D (dat, obj);
     802        break;
     803      case DWG_TYPE_POLYLINE_PFACE:
     804        dwg_free_POLYLINE_PFACE (dat, obj);
     805        break;
     806      case DWG_TYPE_POLYLINE_MESH:
     807        dwg_free_POLYLINE_MESH (dat, obj);
     808        break;
     809      case DWG_TYPE_ARC:
     810        dwg_free_ARC (dat, obj);
     811        break;
     812      case DWG_TYPE_CIRCLE:
     813        dwg_free_CIRCLE (dat, obj);
     814        break;
     815      case DWG_TYPE_LINE:
     816        dwg_free_LINE (dat, obj);
     817        break;
     818      case DWG_TYPE_DIMENSION_ORDINATE:
     819        dwg_free_DIMENSION_ORDINATE (dat, obj);
     820        break;
     821      case DWG_TYPE_DIMENSION_LINEAR:
     822        dwg_free_DIMENSION_LINEAR (dat, obj);
     823        break;
     824      case DWG_TYPE_DIMENSION_ALIGNED:
     825        dwg_free_DIMENSION_ALIGNED (dat, obj);
     826        break;
     827      case DWG_TYPE_DIMENSION_ANG3PT:
     828        dwg_free_DIMENSION_ANG3PT (dat, obj);
     829        break;
     830      case DWG_TYPE_DIMENSION_ANG2LN:
     831        dwg_free_DIMENSION_ANG2LN (dat, obj);
     832        break;
     833      case DWG_TYPE_DIMENSION_RADIUS:
     834        dwg_free_DIMENSION_RADIUS (dat, obj);
     835        break;
     836      case DWG_TYPE_DIMENSION_DIAMETER:
     837        dwg_free_DIMENSION_DIAMETER (dat, obj);
     838        break;
     839      case DWG_TYPE_POINT:
     840        dwg_free_POINT (dat, obj);
     841        break;
     842      case DWG_TYPE__3DFACE:
     843        dwg_free__3DFACE (dat, obj);
     844        break;
     845      case DWG_TYPE__3DLINE:
     846        dwg_free__3DLINE (dat, obj);
     847        break;
     848      case DWG_TYPE_SOLID:
     849        dwg_free_SOLID (dat, obj);
     850        break;
     851      case DWG_TYPE_TRACE:
     852        dwg_free_TRACE (dat, obj);
     853        break;
     854      case DWG_TYPE_SHAPE:
     855        dwg_free_SHAPE (dat, obj);
     856        break;
     857      case DWG_TYPE_VIEWPORT:
     858        dwg_free_VIEWPORT (dat, obj);
     859        break;
     860      case DWG_TYPE_BLOCK_CONTROL:
     861        // _ctrl->entries
     862        dwg_free_BLOCK_CONTROL (dat, obj);
     863        break;
     864      case DWG_TYPE_BLOCK_HEADER:
     865        dwg_free_BLOCK_HEADER (dat, obj);
     866        break;
     867      case DWG_TYPE_LAYER_CONTROL:
     868        dwg_free_LAYER_CONTROL (dat, obj);
     869        break;
     870      case DWG_TYPE_LAYER:
     871        dwg_free_LAYER (dat, obj);
     872        break;
     873      case DWG_TYPE_STYLE_CONTROL:
     874        dwg_free_STYLE_CONTROL (dat, obj);
     875        break;
     876      case DWG_TYPE_STYLE:
     877        dwg_free_STYLE (dat, obj);
     878        break;
     879      case DWG_TYPE_LTYPE_CONTROL:
     880        dwg_free_LTYPE_CONTROL (dat, obj);
     881        break;
     882      case DWG_TYPE_LTYPE:
     883        dwg_free_LTYPE (dat, obj);
     884        break;
     885      case DWG_TYPE_VIEW_CONTROL:
     886        dwg_free_VIEW_CONTROL (dat, obj);
     887        break;
     888      case DWG_TYPE_VIEW:
     889        dwg_free_VIEW (dat, obj);
     890        break;
     891      case DWG_TYPE_UCS_CONTROL:
     892        dwg_free_UCS_CONTROL (dat, obj);
     893        break;
     894      case DWG_TYPE_UCS:
     895        dwg_free_UCS (dat, obj);
     896        break;
     897      case DWG_TYPE_VPORT_CONTROL:
     898        dwg_free_VPORT_CONTROL (dat, obj);
     899        break;
     900      case DWG_TYPE_VPORT:
     901        dwg_free_VPORT (dat, obj);
     902        break;
     903      case DWG_TYPE_APPID_CONTROL:
     904        dwg_free_APPID_CONTROL (dat, obj);
     905        break;
     906      case DWG_TYPE_APPID:
     907        dwg_free_APPID (dat, obj);
     908        break;
     909      case DWG_TYPE_DIMSTYLE_CONTROL:
     910        dwg_free_DIMSTYLE_CONTROL (dat, obj);
     911        break;
     912      case DWG_TYPE_DIMSTYLE:
     913        dwg_free_DIMSTYLE (dat, obj);
     914        break;
     915      case DWG_TYPE_VX_CONTROL:
     916        dwg_free_VX_CONTROL (dat, obj);
     917        break;
     918      case DWG_TYPE_VX_TABLE_RECORD:
     919        dwg_free_VX_TABLE_RECORD (dat, obj);
     920        break;
     921      case DWG_TYPE_LOAD:
     922        dwg_free_LOAD (dat, obj);
     923        break;
     924      case DWG_TYPE_JUMP:
     925        dwg_free_JUMP (dat, obj);
     926        break;
     927      case DWG_TYPE_DICTIONARY:
     928        dwg_free_DICTIONARY (dat, obj);
     929        break;
     930      case DWG_TYPE_UNUSED:
     931        // deleted entity. leak? see above
     932        break;
     933      default:
     934        LOG_ERROR (
     935            "Unhandled preR13 class %s, fixedtype %d in free_preR13_object()",
     936            dwg_type_name (obj->fixedtype), (int)obj->fixedtype);
     937      }
     938  
     939    /* With indxf and injson the dxfname is dynamic, just the name is const */
     940    if (dwg->opts & DWG_OPTS_IN)
     941      FREE_IF (obj->dxfname);
     942    /* With injson even the name is dynamic */
     943    if (dwg->opts & DWG_OPTS_INJSON)
     944      FREE_IF (obj->name);
     945    obj->type = DWG_TYPE_FREED;
     946  }
     947  
     948  // using the global dat
     949  EXPORT void
     950  dwg_free_object (Dwg_Object *obj)
     951  {
     952    int error = 0;
     953    long unsigned int j;
     954    Dwg_Data *dwg;
     955    Bit_Chain *dat = &pdat;
     956  
     957    if (obj && obj->parent)
     958      {
     959        dwg = obj->parent;
     960        dat->version = dwg->header.version;
     961        dat->from_version = dwg->header.from_version;
     962      }
     963    else
     964      return;
     965    if (obj->type == DWG_TYPE_FREED || obj->tio.object == NULL)
     966      return;
     967  
     968    PRE (R_13b1)
     969    {
     970      free_preR13_object (obj);
     971      return;
     972    }
     973    if (obj->fixedtype == DWG_TYPE_TABLESTYLE
     974        && dwg->header.from_version > R_2007)
     975      {
     976        free_TABLESTYLE_r2010 (dat, obj);
     977      }
     978    switch (obj->type)
     979      {
     980      case DWG_TYPE_TEXT:
     981        dwg_free_TEXT (dat, obj);
     982        break;
     983      case DWG_TYPE_ATTRIB:
     984        dwg_free_ATTRIB (dat, obj);
     985        break;
     986      case DWG_TYPE_ATTDEF:
     987        dwg_free_ATTDEF (dat, obj);
     988        break;
     989      case DWG_TYPE_BLOCK:
     990        dwg_free_BLOCK (dat, obj);
     991        break;
     992      case DWG_TYPE_ENDBLK:
     993        dwg_free_ENDBLK (dat, obj);
     994        break;
     995      case DWG_TYPE_SEQEND:
     996        dwg_free_SEQEND (dat, obj);
     997        break;
     998      case DWG_TYPE_INSERT:
     999        dwg_free_INSERT (dat, obj);
    1000        break;
    1001      case DWG_TYPE_MINSERT:
    1002        dwg_free_MINSERT (dat, obj);
    1003        break;
    1004      case DWG_TYPE_VERTEX_2D:
    1005        dwg_free_VERTEX_2D (dat, obj);
    1006        break;
    1007      case DWG_TYPE_VERTEX_3D:
    1008        dwg_free_VERTEX_3D (dat, obj);
    1009        break;
    1010      case DWG_TYPE_VERTEX_MESH:
    1011        dwg_free_VERTEX_MESH (dat, obj);
    1012        break;
    1013      case DWG_TYPE_VERTEX_PFACE:
    1014        dwg_free_VERTEX_PFACE (dat, obj);
    1015        break;
    1016      case DWG_TYPE_VERTEX_PFACE_FACE:
    1017        dwg_free_VERTEX_PFACE_FACE (dat, obj);
    1018        break;
    1019      case DWG_TYPE_POLYLINE_2D:
    1020        dwg_free_POLYLINE_2D (dat, obj);
    1021        break;
    1022      case DWG_TYPE_POLYLINE_3D:
    1023        dwg_free_POLYLINE_3D (dat, obj);
    1024        break;
    1025      case DWG_TYPE_ARC:
    1026        dwg_free_ARC (dat, obj);
    1027        break;
    1028      case DWG_TYPE_CIRCLE:
    1029        dwg_free_CIRCLE (dat, obj);
    1030        break;
    1031      case DWG_TYPE_LINE:
    1032        dwg_free_LINE (dat, obj);
    1033        break;
    1034      case DWG_TYPE_DIMENSION_ORDINATE:
    1035        dwg_free_DIMENSION_ORDINATE (dat, obj);
    1036        break;
    1037      case DWG_TYPE_DIMENSION_LINEAR:
    1038        dwg_free_DIMENSION_LINEAR (dat, obj);
    1039        break;
    1040      case DWG_TYPE_DIMENSION_ALIGNED:
    1041        dwg_free_DIMENSION_ALIGNED (dat, obj);
    1042        break;
    1043      case DWG_TYPE_DIMENSION_ANG3PT:
    1044        dwg_free_DIMENSION_ANG3PT (dat, obj);
    1045        break;
    1046      case DWG_TYPE_DIMENSION_ANG2LN:
    1047        dwg_free_DIMENSION_ANG2LN (dat, obj);
    1048        break;
    1049      case DWG_TYPE_DIMENSION_RADIUS:
    1050        dwg_free_DIMENSION_RADIUS (dat, obj);
    1051        break;
    1052      case DWG_TYPE_DIMENSION_DIAMETER:
    1053        dwg_free_DIMENSION_DIAMETER (dat, obj);
    1054        break;
    1055      case DWG_TYPE_POINT:
    1056        dwg_free_POINT (dat, obj);
    1057        break;
    1058      case DWG_TYPE__3DFACE:
    1059        dwg_free__3DFACE (dat, obj);
    1060        break;
    1061      case DWG_TYPE_POLYLINE_PFACE:
    1062        dwg_free_POLYLINE_PFACE (dat, obj);
    1063        break;
    1064      case DWG_TYPE_POLYLINE_MESH:
    1065        dwg_free_POLYLINE_MESH (dat, obj);
    1066        break;
    1067      case DWG_TYPE_SOLID:
    1068        dwg_free_SOLID (dat, obj);
    1069        break;
    1070      case DWG_TYPE_TRACE:
    1071        dwg_free_TRACE (dat, obj);
    1072        break;
    1073      case DWG_TYPE_SHAPE:
    1074        dwg_free_SHAPE (dat, obj);
    1075        break;
    1076      case DWG_TYPE_VIEWPORT:
    1077        dwg_free_VIEWPORT (dat, obj);
    1078        break;
    1079      case DWG_TYPE_ELLIPSE:
    1080        dwg_free_ELLIPSE (dat, obj);
    1081        break;
    1082      case DWG_TYPE_SPLINE:
    1083        dwg_free_SPLINE (dat, obj);
    1084        break;
    1085      case DWG_TYPE_REGION:
    1086        dwg_free_REGION (dat, obj);
    1087        break;
    1088      case DWG_TYPE__3DSOLID:
    1089        dwg_free__3DSOLID (dat, obj);
    1090        break; /* Check the type of the object */
    1091      case DWG_TYPE_BODY:
    1092        dwg_free_BODY (dat, obj);
    1093        break;
    1094      case DWG_TYPE_RAY:
    1095        dwg_free_RAY (dat, obj);
    1096        break;
    1097      case DWG_TYPE_XLINE:
    1098        dwg_free_XLINE (dat, obj);
    1099        break;
    1100      case DWG_TYPE_DICTIONARY:
    1101        dwg_free_DICTIONARY (dat, obj);
    1102        break;
    1103      case DWG_TYPE_MTEXT:
    1104        dwg_free_MTEXT (dat, obj);
    1105        break;
    1106      case DWG_TYPE_LEADER:
    1107        dwg_free_LEADER (dat, obj);
    1108        break;
    1109      case DWG_TYPE_TOLERANCE:
    1110        dwg_free_TOLERANCE (dat, obj);
    1111        break;
    1112      case DWG_TYPE_MLINE:
    1113        dwg_free_MLINE (dat, obj);
    1114        break;
    1115      case DWG_TYPE_BLOCK_CONTROL:
    1116        dwg_free_BLOCK_CONTROL (dat, obj);
    1117        break;
    1118      case DWG_TYPE_BLOCK_HEADER:
    1119        dwg_free_BLOCK_HEADER (dat, obj);
    1120        break;
    1121      case DWG_TYPE_LAYER_CONTROL:
    1122        dwg_free_LAYER_CONTROL (dat, obj);
    1123        break;
    1124      case DWG_TYPE_LAYER:
    1125        dwg_free_LAYER (dat, obj);
    1126        break;
    1127      case DWG_TYPE_STYLE_CONTROL:
    1128        dwg_free_STYLE_CONTROL (dat, obj);
    1129        break;
    1130      case DWG_TYPE_STYLE:
    1131        dwg_free_STYLE (dat, obj);
    1132        break;
    1133      case DWG_TYPE_LTYPE_CONTROL:
    1134        dwg_free_LTYPE_CONTROL (dat, obj);
    1135        break;
    1136      case DWG_TYPE_LTYPE:
    1137        dwg_free_LTYPE (dat, obj);
    1138        break;
    1139      case DWG_TYPE_VIEW_CONTROL:
    1140        dwg_free_VIEW_CONTROL (dat, obj);
    1141        break;
    1142      case DWG_TYPE_VIEW:
    1143        dwg_free_VIEW (dat, obj);
    1144        break;
    1145      case DWG_TYPE_UCS_CONTROL:
    1146        dwg_free_UCS_CONTROL (dat, obj);
    1147        break;
    1148      case DWG_TYPE_UCS:
    1149        dwg_free_UCS (dat, obj);
    1150        break;
    1151      case DWG_TYPE_VPORT_CONTROL:
    1152        dwg_free_VPORT_CONTROL (dat, obj);
    1153        break;
    1154      case DWG_TYPE_VPORT:
    1155        dwg_free_VPORT (dat, obj);
    1156        break;
    1157      case DWG_TYPE_APPID_CONTROL:
    1158        dwg_free_APPID_CONTROL (dat, obj);
    1159        break;
    1160      case DWG_TYPE_APPID:
    1161        dwg_free_APPID (dat, obj);
    1162        break;
    1163      case DWG_TYPE_DIMSTYLE_CONTROL:
    1164        dwg_free_DIMSTYLE_CONTROL (dat, obj);
    1165        break;
    1166      case DWG_TYPE_DIMSTYLE:
    1167        dwg_free_DIMSTYLE (dat, obj);
    1168        break;
    1169      case DWG_TYPE_VX_CONTROL:
    1170        dwg_free_VX_CONTROL (dat, obj);
    1171        break;
    1172      case DWG_TYPE_VX_TABLE_RECORD:
    1173        dwg_free_VX_TABLE_RECORD (dat, obj);
    1174        break;
    1175      case DWG_TYPE_GROUP:
    1176        dwg_free_GROUP (dat, obj);
    1177        break;
    1178      case DWG_TYPE_MLINESTYLE:
    1179        dwg_free_MLINESTYLE (dat, obj);
    1180        break;
    1181      case DWG_TYPE_OLE2FRAME:
    1182        dwg_free_OLE2FRAME (dat, obj);
    1183        break;
    1184      case DWG_TYPE_DUMMY:
    1185        dwg_free_DUMMY (dat, obj);
    1186        break;
    1187      case DWG_TYPE_LONG_TRANSACTION:
    1188        dwg_free_LONG_TRANSACTION (dat, obj);
    1189        break;
    1190      case DWG_TYPE_LWPOLYLINE:
    1191        dwg_free_LWPOLYLINE (dat, obj);
    1192        break;
    1193      case DWG_TYPE_HATCH:
    1194        dwg_free_HATCH (dat, obj);
    1195        break;
    1196      case DWG_TYPE_XRECORD:
    1197        dwg_free_XRECORD (dat, obj);
    1198        break;
    1199      case DWG_TYPE_PLACEHOLDER:
    1200        dwg_free_PLACEHOLDER (dat, obj);
    1201        break;
    1202      case DWG_TYPE_OLEFRAME:
    1203        dwg_free_OLEFRAME (dat, obj);
    1204        break;
    1205  #ifdef DEBUG_VBA_PROJECT
    1206      case DWG_TYPE_VBA_PROJECT:
    1207        dwg_free_VBA_PROJECT (dat, obj);
    1208        break;
    1209  #endif
    1210      case DWG_TYPE_LAYOUT:
    1211        dwg_free_LAYOUT (dat, obj);
    1212        break;
    1213      case DWG_TYPE_PROXY_ENTITY:
    1214        dwg_free_PROXY_ENTITY (dat, obj);
    1215        break;
    1216      case DWG_TYPE_PROXY_OBJECT:
    1217        dwg_free_PROXY_OBJECT (dat, obj);
    1218        break;
    1219      default:
    1220        if (obj->type == obj->parent->layout_type
    1221            && obj->fixedtype == DWG_TYPE_LAYOUT)
    1222          {
    1223            SINCE (R_13b1)
    1224            {
    1225              dwg_free_LAYOUT (dat, obj); // XXX avoid double-free, esp. in eed
    1226            }
    1227          }
    1228        else if ((error = dwg_free_variable_type (obj->parent, obj))
    1229                 & DWG_ERR_UNHANDLEDCLASS)
    1230          {
    1231            if (obj->fixedtype == DWG_TYPE_UNKNOWN_ENT)
    1232              dwg_free_UNKNOWN_ENT (dat, obj);
    1233            else if (obj->fixedtype == DWG_TYPE_UNKNOWN_OBJ)
    1234              dwg_free_UNKNOWN_OBJ (dat, obj);
    1235          }
    1236      }
    1237    /* With indxf the dxfname is dynamic, just the name is const */
    1238    if ((dwg->opts & DWG_OPTS_INDXF) || (dwg->opts & DWG_OPTS_INJSON))
    1239      FREE_IF (obj->dxfname);
    1240    /* With injson even the name is dynamic */
    1241    if (dwg->opts & DWG_OPTS_INJSON)
    1242      FREE_IF (obj->name);
    1243    obj->type = DWG_TYPE_FREED;
    1244  }
    1245  
    1246  /* Needed when we cast types.
    1247     By fixedtype, not dxfname.
    1248   */
    1249  EXPORT void
    1250  dwg_free_object_private (Dwg_Object *obj)
    1251  {
    1252    int error = 0;
    1253    long unsigned int j;
    1254    Dwg_Data *dwg;
    1255    Bit_Chain *dat = &pdat;
    1256  
    1257    if (obj && obj->parent)
    1258      {
    1259        dwg = obj->parent;
    1260        dat->version = dwg->header.version;
    1261        dat->from_version = dwg->header.from_version;
    1262      }
    1263    else
    1264      return;
    1265    if (obj->type == DWG_TYPE_FREED || obj->tio.object == NULL)
    1266      return;
    1267  
    1268    switch (obj->type)
    1269      {
    1270      case DWG_TYPE_TEXT:
    1271        dwg_free_TEXT_private (dat, dat, dat, obj);
    1272        break;
    1273      case DWG_TYPE_ATTRIB:
    1274        dwg_free_ATTRIB_private (dat, dat, dat, obj);
    1275        break;
    1276      case DWG_TYPE_ATTDEF:
    1277        dwg_free_ATTDEF_private (dat, dat, dat, obj);
    1278        break;
    1279      case DWG_TYPE_BLOCK:
    1280        dwg_free_BLOCK_private (dat, dat, dat, obj);
    1281        break;
    1282      case DWG_TYPE_ENDBLK:
    1283        dwg_free_ENDBLK_private (dat, dat, dat, obj);
    1284        break;
    1285      case DWG_TYPE_SEQEND:
    1286        dwg_free_SEQEND_private (dat, dat, dat, obj);
    1287        break;
    1288      case DWG_TYPE_INSERT:
    1289        dwg_free_INSERT_private (dat, dat, dat, obj);
    1290        break;
    1291      case DWG_TYPE_MINSERT:
    1292        dwg_free_MINSERT_private (dat, dat, dat, obj);
    1293        break;
    1294      case DWG_TYPE_VERTEX_2D:
    1295        dwg_free_VERTEX_2D_private (dat, dat, dat, obj);
    1296        break;
    1297      case DWG_TYPE_VERTEX_3D:
    1298        dwg_free_VERTEX_3D_private (dat, dat, dat, obj);
    1299        break;
    1300      case DWG_TYPE_VERTEX_MESH:
    1301        dwg_free_VERTEX_MESH_private (dat, dat, dat, obj);
    1302        break;
    1303      case DWG_TYPE_VERTEX_PFACE:
    1304        dwg_free_VERTEX_PFACE_private (dat, dat, dat, obj);
    1305        break;
    1306      case DWG_TYPE_VERTEX_PFACE_FACE:
    1307        dwg_free_VERTEX_PFACE_FACE_private (dat, dat, dat, obj);
    1308        break;
    1309      case DWG_TYPE_POLYLINE_2D:
    1310        dwg_free_POLYLINE_2D_private (dat, dat, dat, obj);
    1311        break;
    1312      case DWG_TYPE_POLYLINE_3D:
    1313        dwg_free_POLYLINE_3D_private (dat, dat, dat, obj);
    1314        break;
    1315      case DWG_TYPE_ARC:
    1316        dwg_free_ARC_private (dat, dat, dat, obj);
    1317        break;
    1318      case DWG_TYPE_CIRCLE:
    1319        dwg_free_CIRCLE_private (dat, dat, dat, obj);
    1320        break;
    1321      case DWG_TYPE_LINE:
    1322        dwg_free_LINE_private (dat, dat, dat, obj);
    1323        break;
    1324      case DWG_TYPE_DIMENSION_ORDINATE:
    1325        dwg_free_DIMENSION_ORDINATE_private (dat, dat, dat, obj);
    1326        break;
    1327      case DWG_TYPE_DIMENSION_LINEAR:
    1328        dwg_free_DIMENSION_LINEAR_private (dat, dat, dat, obj);
    1329        break;
    1330      case DWG_TYPE_DIMENSION_ALIGNED:
    1331        dwg_free_DIMENSION_ALIGNED_private (dat, dat, dat, obj);
    1332        break;
    1333      case DWG_TYPE_DIMENSION_ANG3PT:
    1334        dwg_free_DIMENSION_ANG3PT_private (dat, dat, dat, obj);
    1335        break;
    1336      case DWG_TYPE_DIMENSION_ANG2LN:
    1337        dwg_free_DIMENSION_ANG2LN_private (dat, dat, dat, obj);
    1338        break;
    1339      case DWG_TYPE_DIMENSION_RADIUS:
    1340        dwg_free_DIMENSION_RADIUS_private (dat, dat, dat, obj);
    1341        break;
    1342      case DWG_TYPE_DIMENSION_DIAMETER:
    1343        dwg_free_DIMENSION_DIAMETER_private (dat, dat, dat, obj);
    1344        break;
    1345      case DWG_TYPE_POINT:
    1346        dwg_free_POINT_private (dat, dat, dat, obj);
    1347        break;
    1348      case DWG_TYPE__3DFACE:
    1349        dwg_free__3DFACE_private (dat, dat, dat, obj);
    1350        break;
    1351      case DWG_TYPE_POLYLINE_PFACE:
    1352        dwg_free_POLYLINE_PFACE_private (dat, dat, dat, obj);
    1353        break;
    1354      case DWG_TYPE_POLYLINE_MESH:
    1355        dwg_free_POLYLINE_MESH_private (dat, dat, dat, obj);
    1356        break;
    1357      case DWG_TYPE_SOLID:
    1358        dwg_free_SOLID_private (dat, dat, dat, obj);
    1359        break;
    1360      case DWG_TYPE_TRACE:
    1361        dwg_free_TRACE_private (dat, dat, dat, obj);
    1362        break;
    1363      case DWG_TYPE_SHAPE:
    1364        dwg_free_SHAPE_private (dat, dat, dat, obj);
    1365        break;
    1366      case DWG_TYPE_VIEWPORT:
    1367        dwg_free_VIEWPORT_private (dat, dat, dat, obj);
    1368        break;
    1369      case DWG_TYPE_ELLIPSE:
    1370        dwg_free_ELLIPSE_private (dat, dat, dat, obj);
    1371        break;
    1372      case DWG_TYPE_SPLINE:
    1373        dwg_free_SPLINE_private (dat, dat, dat, obj);
    1374        break;
    1375      case DWG_TYPE_REGION:
    1376        dwg_free_REGION_private (dat, dat, dat, obj);
    1377        break;
    1378      case DWG_TYPE__3DSOLID:
    1379        dwg_free__3DSOLID_private (dat, dat, dat, obj);
    1380        break; /* Check the type of the object */
    1381      case DWG_TYPE_BODY:
    1382        dwg_free_BODY_private (dat, dat, dat, obj);
    1383        break;
    1384      case DWG_TYPE_RAY:
    1385        dwg_free_RAY_private (dat, dat, dat, obj);
    1386        break;
    1387      case DWG_TYPE_XLINE:
    1388        dwg_free_XLINE_private (dat, dat, dat, obj);
    1389        break;
    1390      case DWG_TYPE_DICTIONARY:
    1391        dwg_free_DICTIONARY_private (dat, dat, dat, obj);
    1392        break;
    1393      case DWG_TYPE_MTEXT:
    1394        dwg_free_MTEXT_private (dat, dat, dat, obj);
    1395        break;
    1396      case DWG_TYPE_LEADER:
    1397        dwg_free_LEADER_private (dat, dat, dat, obj);
    1398        break;
    1399      case DWG_TYPE_TOLERANCE:
    1400        dwg_free_TOLERANCE_private (dat, dat, dat, obj);
    1401        break;
    1402      case DWG_TYPE_MLINE:
    1403        dwg_free_MLINE_private (dat, dat, dat, obj);
    1404        break;
    1405      case DWG_TYPE_BLOCK_CONTROL:
    1406        dwg_free_BLOCK_CONTROL_private (dat, dat, dat, obj);
    1407        break;
    1408      case DWG_TYPE_BLOCK_HEADER:
    1409        dwg_free_BLOCK_HEADER_private (dat, dat, dat, obj);
    1410        break;
    1411      case DWG_TYPE_LAYER_CONTROL:
    1412        dwg_free_LAYER_CONTROL_private (dat, dat, dat, obj);
    1413        break;
    1414      case DWG_TYPE_LAYER:
    1415        dwg_free_LAYER_private (dat, dat, dat, obj);
    1416        break;
    1417      case DWG_TYPE_STYLE_CONTROL:
    1418        dwg_free_STYLE_CONTROL_private (dat, dat, dat, obj);
    1419        break;
    1420      case DWG_TYPE_STYLE:
    1421        dwg_free_STYLE_private (dat, dat, dat, obj);
    1422        break;
    1423      case DWG_TYPE_LTYPE_CONTROL:
    1424        dwg_free_LTYPE_CONTROL_private (dat, dat, dat, obj);
    1425        break;
    1426      case DWG_TYPE_LTYPE:
    1427        dwg_free_LTYPE_private (dat, dat, dat, obj);
    1428        break;
    1429      case DWG_TYPE_VIEW_CONTROL:
    1430        dwg_free_VIEW_CONTROL_private (dat, dat, dat, obj);
    1431        break;
    1432      case DWG_TYPE_VIEW:
    1433        dwg_free_VIEW_private (dat, dat, dat, obj);
    1434        break;
    1435      case DWG_TYPE_UCS_CONTROL:
    1436        dwg_free_UCS_CONTROL_private (dat, dat, dat, obj);
    1437        break;
    1438      case DWG_TYPE_UCS:
    1439        dwg_free_UCS_private (dat, dat, dat, obj);
    1440        break;
    1441      case DWG_TYPE_VPORT_CONTROL:
    1442        dwg_free_VPORT_CONTROL_private (dat, dat, dat, obj);
    1443        break;
    1444      case DWG_TYPE_VPORT:
    1445        dwg_free_VPORT_private (dat, dat, dat, obj);
    1446        break;
    1447      case DWG_TYPE_APPID_CONTROL:
    1448        dwg_free_APPID_CONTROL_private (dat, dat, dat, obj);
    1449        break;
    1450      case DWG_TYPE_APPID:
    1451        dwg_free_APPID_private (dat, dat, dat, obj);
    1452        break;
    1453      case DWG_TYPE_DIMSTYLE_CONTROL:
    1454        dwg_free_DIMSTYLE_CONTROL_private (dat, dat, dat, obj);
    1455        break;
    1456      case DWG_TYPE_DIMSTYLE:
    1457        dwg_free_DIMSTYLE_private (dat, dat, dat, obj);
    1458        break;
    1459      case DWG_TYPE_VX_CONTROL:
    1460        dwg_free_VX_CONTROL_private (dat, dat, dat, obj);
    1461        break;
    1462      case DWG_TYPE_VX_TABLE_RECORD:
    1463        dwg_free_VX_TABLE_RECORD_private (dat, dat, dat, obj);
    1464        break;
    1465      case DWG_TYPE_GROUP:
    1466        dwg_free_GROUP_private (dat, dat, dat, obj);
    1467        break;
    1468      case DWG_TYPE_MLINESTYLE:
    1469        dwg_free_MLINESTYLE_private (dat, dat, dat, obj);
    1470        break;
    1471      case DWG_TYPE_OLE2FRAME:
    1472        dwg_free_OLE2FRAME_private (dat, dat, dat, obj);
    1473        break;
    1474      case DWG_TYPE_DUMMY:
    1475        dwg_free_DUMMY_private (dat, dat, dat, obj);
    1476        break;
    1477      case DWG_TYPE_LONG_TRANSACTION:
    1478        dwg_free_LONG_TRANSACTION_private (dat, dat, dat, obj);
    1479        break;
    1480      case DWG_TYPE_LWPOLYLINE:
    1481        dwg_free_LWPOLYLINE_private (dat, dat, dat, obj);
    1482        break;
    1483      case DWG_TYPE_HATCH:
    1484        dwg_free_HATCH_private (dat, dat, dat, obj);
    1485        break;
    1486      case DWG_TYPE_XRECORD:
    1487        dwg_free_XRECORD_private (dat, dat, dat, obj);
    1488        break;
    1489      case DWG_TYPE_PLACEHOLDER:
    1490        dwg_free_PLACEHOLDER_private (dat, dat, dat, obj);
    1491        break;
    1492      case DWG_TYPE_OLEFRAME:
    1493        dwg_free_OLEFRAME_private (dat, dat, dat, obj);
    1494        break;
    1495  #ifdef DEBUG_VBA_PROJECT
    1496      case DWG_TYPE_VBA_PROJECT:
    1497        dwg_free_VBA_PROJECT_private (dat, dat, dat, obj);
    1498        break;
    1499  #endif
    1500      case DWG_TYPE_LAYOUT:
    1501        dwg_free_LAYOUT_private (dat, dat, dat, obj);
    1502        break;
    1503      case DWG_TYPE_PROXY_ENTITY:
    1504        dwg_free_PROXY_ENTITY_private (dat, dat, dat, obj);
    1505        break;
    1506      case DWG_TYPE_PROXY_OBJECT:
    1507        dwg_free_PROXY_OBJECT_private (dat, dat, dat, obj);
    1508        break;
    1509      default:
    1510        if (obj->type == obj->parent->layout_type
    1511            && obj->fixedtype == DWG_TYPE_LAYOUT)
    1512          {
    1513            SINCE (R_13b1)
    1514            {
    1515              dwg_free_LAYOUT_private (
    1516                  dat, dat, dat, obj); // XXX avoid double-free, esp. in eed
    1517            }
    1518          }
    1519        else
    1520          dwg_free_variable_type_private (obj);
    1521      }
    1522  }
    1523  
    1524  static int
    1525  dwg_free_preR13_header_vars (Dwg_Data *dwg)
    1526  {
    1527    Dwg_Header_Variables *_obj = &dwg->header_vars;
    1528    Dwg_Object *obj = NULL;
    1529    Bit_Chain *dat = &pdat;
    1530    int error = 0;
    1531  
    1532    // fields added by dwg_add_Document:
    1533    FIELD_TV (MENU, 0);
    1534  
    1535    // clang-format off
    1536    #include "header_variables_r11.spec"
    1537    // clang-format on
    1538  
    1539    return 0;
    1540  }
    1541  
    1542  static int
    1543  dwg_free_header_vars (Dwg_Data *dwg)
    1544  {
    1545    Dwg_Header_Variables *_obj = &dwg->header_vars;
    1546    Dwg_Object *obj = NULL;
    1547    Bit_Chain *dat = &pdat;
    1548  
    1549    // clang-format off
    1550    #include "header_variables.spec"
    1551    // clang-format on
    1552  
    1553    FIELD_TV (DWGCODEPAGE, 0);
    1554    return 0;
    1555  }
    1556  
    1557  static int
    1558  dwg_free_summaryinfo (Dwg_Data *dwg)
    1559  {
    1560    Dwg_SummaryInfo *_obj = &dwg->summaryinfo;
    1561    Dwg_Object *obj = NULL;
    1562    Bit_Chain *dat = &pdat;
    1563  
    1564  // clang-format off
    1565    #include "summaryinfo.spec"
    1566    // clang-format on
    1567    return 0;
    1568  }
    1569  
    1570  static int
    1571  dwg_free_appinfo (Dwg_Data *dwg)
    1572  {
    1573    Dwg_AppInfo *_obj = &dwg->appinfo;
    1574    Dwg_Object *obj = NULL;
    1575    Bit_Chain *dat = &pdat;
    1576  
    1577  // clang-format off
    1578    #include "appinfo.spec"
    1579    // clang-format on
    1580    return 0;
    1581  }
    1582  static int
    1583  dwg_free_filedeplist (Dwg_Data *dwg)
    1584  {
    1585    Dwg_FileDepList *_obj = &dwg->filedeplist;
    1586    Dwg_Object *obj = NULL;
    1587    Bit_Chain *dat = &pdat;
    1588    BITCODE_RL vcount;
    1589  
    1590  // clang-format off
    1591    #include "filedeplist.spec"
    1592    // clang-format on
    1593    return 0;
    1594  }
    1595  static int
    1596  dwg_free_security (Dwg_Data *dwg)
    1597  {
    1598    Dwg_Security *_obj = &dwg->security;
    1599    Dwg_Object *obj = NULL;
    1600    Bit_Chain *dat = &pdat;
    1601  
    1602  // clang-format off
    1603    #include "security.spec"
    1604    // clang-format on
    1605    return 0;
    1606  }
    1607  
    1608  static int
    1609  dwg_free_acds (Dwg_Data *dwg)
    1610  {
    1611    Dwg_AcDs *_obj = &dwg->acds;
    1612    Dwg_Object *obj = NULL;
    1613    Bit_Chain *dat = &pdat;
    1614    BITCODE_RL rcount3 = 0, rcount4, vcount;
    1615    int error = 0;
    1616  
    1617  // clang-format off
    1618    #include "acds.spec"
    1619    // clang-format on
    1620    return 0;
    1621  }
    1622  
    1623  void
    1624  dwg_free (Dwg_Data *dwg)
    1625  {
    1626    BITCODE_BL i;
    1627    if (dwg)
    1628      {
    1629        pdat.version = dwg->header.version;
    1630        pdat.from_version = dwg->header.from_version;
    1631        if (dwg->opts)
    1632          {
    1633            loglevel = dwg->opts & DWG_OPTS_LOGLEVEL;
    1634            pdat.opts = dwg->opts;
    1635          }
    1636  #ifdef USE_TRACING
    1637        /* Before starting, set the logging level, but only do so once.  */
    1638        if (!env_var_checked_p)
    1639          {
    1640            char *probe = getenv ("LIBREDWG_TRACE");
    1641            if (probe)
    1642              loglevel = atoi (probe);
    1643            env_var_checked_p = 1;
    1644          }
    1645  #endif /* USE_TRACING */
    1646        LOG_INFO ("\n============\ndwg_free\n")
    1647        // copied table fields have duplicate pointers, but are freed only once
    1648        for (i = 0; i < dwg->num_objects; ++i)
    1649          {
    1650            if (!dwg_obj_is_control (&dwg->object[i]))
    1651              dwg_free_object (&dwg->object[i]);
    1652          }
    1653        if (dwg->header.version < R_13b1)
    1654          dwg_free_preR13_header_vars (dwg);
    1655        else
    1656          dwg_free_header_vars (dwg);
    1657        dwg_free_summaryinfo (dwg);
    1658        if (dwg->header.section_infohdr.num_desc)
    1659          {
    1660            for (i = 0; i < dwg->header.section_infohdr.num_desc; ++i)
    1661              FREE_IF (dwg->header.section_info[i].sections);
    1662            FREE_IF (dwg->header.section_info);
    1663          }
    1664        dwg_free_appinfo (dwg);
    1665        dwg_free_filedeplist (dwg);
    1666        dwg_free_security (dwg);
    1667        dwg_free_acds (dwg);
    1668  
    1669        FREE_IF (dwg->thumbnail.chain);
    1670        FREE_IF (dwg->vbaproject.unknown_bits);
    1671        FREE_IF (dwg->revhistory.histories);
    1672        FREE_IF (dwg->appinfohistory.unknown_bits);
    1673        // FREE_IF (dwg->objfreespace...);
    1674        FREE_IF (dwg->Template.description);
    1675        FREE_IF (dwg->header.section);
    1676        FREE_IF (dwg->auxheader.R11_HANDSEED);
    1677  
    1678        for (i = 0; i < dwg->num_objects; ++i)
    1679          {
    1680            if (dwg_obj_is_control (&dwg->object[i]))
    1681              dwg_free_object (&dwg->object[i]);
    1682          }
    1683        if (dwg->num_classes && dwg->dwg_class)
    1684          {
    1685            for (i = 0; i < dwg->num_classes; ++i)
    1686              {
    1687                FREE_IF (dwg->dwg_class[i].appname);
    1688                FREE_IF (dwg->dwg_class[i].cppname);
    1689                FREE_IF (dwg->dwg_class[i].dxfname);
    1690                if (dwg->header.from_version >= R_2007)
    1691                  FREE_IF (dwg->dwg_class[i].dxfname_u);
    1692              }
    1693          }
    1694        FREE_IF (dwg->dwg_class);
    1695        if (dwg->object_ref)
    1696          {
    1697            LOG_HANDLE ("free %d global refs\n", dwg->num_object_refs)
    1698            for (i = 0; i < dwg->num_object_refs; ++i)
    1699              {
    1700                LOG_INSANE ("free ref %d\n", i)
    1701                FREE_IF (dwg->object_ref[i]);
    1702              }
    1703          }
    1704        FREE_IF (dwg->object_ref);
    1705        for (i = 0; i < dwg->num_acis_sab_hdl; ++i)
    1706          {
    1707            FREE_IF (dwg->acis_sab_hdl[i]);
    1708          }
    1709        FREE_IF (dwg->acis_sab_hdl);
    1710        FREE_IF (dwg->object);
    1711        if (dwg->object_map)
    1712          {
    1713            hash_free (dwg->object_map);
    1714            dwg->object_map = NULL;
    1715          }
    1716        dwg->num_objects = dwg->num_classes = dwg->num_object_refs = 0;
    1717  #undef FREE_IF
    1718      }
    1719  }
    1720  
    1721  #undef IS_FREE