DNA parser

Currently almost all blender codebase is in c++, but the central core of DNA still remains in the ancient c struct types and the DNA parser can only parse a limited set of definitions in c.

Problem:
One of the recurring problems is style breakage, many places use common values ​​like FILE_MAX, but current limitations makes impossible the use of macros, making these values ​​to be duplicated in several places, such in CacheFileLayer:

typedef struct CacheFileLayer {
  ...  
 /** 1024 = FILE_MAX. */
  char filepath[1024];
  ...
} CacheFileLayer;

Another problem is that due to the limitations of c and since enums cannot be defined with a fixed size, they are still outside of being supported by the parser.


Proposal:
Looking forward to move DNA files to c++ to, we could start defining and using enums with fixed types like

enum eLightType : short{
  ...
};

enum eEnum : int64_t {
   ...
   Value33 = 1ull<<33,
};

This can remove the constant mixing up and conversions between basic types and enums.
Also macro defines could be gathered and use them instead of duplicate values all over the places.

Experiment: WIP: DNA: makesdna parse is a early proposal for parsing DNA files with simple paser that gathers structs,enums and #defines, and eventually could work with namespace or struct/class member value default initialization.

Given the example code file:


/*---------------------------------------------*/
/** #pragma once and includes */

#pragma once

#include "...."
#include "DNA_ID.h"
#include "DNA_armature_types.h"
#include "DNA_listBase.h"
#include "DNA_session_uid_types.h"
#include "DNA_userdef_types.h"
#include "DNA_vec_types.h"

// Forward declarations
struct Collection;
struct GHash;
struct Object, SpaceLink;

#if 0
typedef enum class UnusedEnum: uint8_t {
  /* vert is selected */
  UNUSED_1 = (1 + 0*FILE_MAX),
  UNUSED_2 = (1 << 1),
} UnusedEnum;
ENUM_OPERATORS(UnusedEnum, UNUSED_2);
#endif


/* Const int define */
#define FILE_MAX 1024

/* define non const int*/
#define DNA_DEFINE_CXX_METHODS() ....

/** bMotionPathVert, taken from DNA_action_Types.h
 * modified with a child struct. */
typedef struct bMotionPathVert {
  DNA_DEFINE_CXX_METHODS(bMotionPathVert);
  /* Child struct */
  struct bMotionPathVertItem {
    DNA_DEFINE_CXX_METHODS(bMotionPathVert);
    float co[3], pre[235];
    struct Link *next, *pre;
    char path[FILE_MAX];
    bool (*poll)(bContext *, ARegion *);
    float (*data_src)[256];
  };
  /** Coordinates of point in 3D-space. */
  float co[3];
  /** Quick settings. */
  int flag;
} bMotionPathVert;

/** eMotionPathVert_Flag, taken from DNA_action_Types.h
 * modified with a fixed size. */
typedef enum class eMotionPathVert_Flag : uint8_t {
  /* vert is selected */
  VERT_SEL = (1 << 0),
  VERT_KEY = (1 << 1),
} eMotionPathVert_Flag;
ENUM_OPERATORS(eMotionPathVert_Flag, VERT_KEY);


Debug output result

#define FILE_MAX 1024
struct bMotionPathVert {
    struct bMotionPathVertItem {
        float co[3],pre[235];
        Link *next,*pre;
        char path[FILE_MAX];
        bool (*poll)(...);
        float (*data_src)[256];
    };
    float co[3];
    int flag;
};
enum eMotionPathVert_Flag: uint8_t {...};

The changes that have been made allows to easily incorporate new formating rules (as namespaces or member functions)

Boost is a soft dependency for us, making it unsuitable for any core component to depend on

I removed the dependency, fmt it is a valid one to use, right?

we ship fmt with the blender code, so you can rely on it being available