Blender  V2.93
blender.c
Go to the documentation of this file.
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
17  * All rights reserved.
18  */
19 
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <string.h>
29 
30 #include "MEM_guardedalloc.h"
31 
32 #include "BLI_listbase.h"
33 #include "BLI_string.h"
34 #include "BLI_utildefines.h"
35 
36 #include "IMB_imbuf.h"
37 #include "IMB_moviecache.h"
38 
39 #include "BKE_addon.h"
40 #include "BKE_blender.h" /* own include */
41 #include "BKE_blender_user_menu.h"
42 #include "BKE_blender_version.h" /* own include */
43 #include "BKE_blendfile.h"
44 #include "BKE_brush.h"
45 #include "BKE_cachefile.h"
46 #include "BKE_callbacks.h"
47 #include "BKE_global.h"
48 #include "BKE_idprop.h"
49 #include "BKE_image.h"
50 #include "BKE_layer.h"
51 #include "BKE_main.h"
52 #include "BKE_node.h"
53 #include "BKE_report.h"
54 #include "BKE_scene.h"
55 #include "BKE_screen.h"
56 #include "BKE_studiolight.h"
57 
58 #include "DEG_depsgraph.h"
59 
60 #include "RE_pipeline.h"
61 #include "RE_texture.h"
62 
63 #include "SEQ_sequencer.h"
64 
65 #include "BLF_api.h"
66 
69 
70 /* -------------------------------------------------------------------- */
74 /* only to be called on exit blender */
75 void BKE_blender_free(void)
76 {
77  /* samples are in a global list..., also sets G_MAIN->sound->sample NULL */
78 
79  /* Needs to run before main free as wm is still referenced for icons preview jobs. */
81 
83  G_MAIN = NULL;
84 
85  if (G.log.file != NULL) {
86  fclose(G.log.file);
87  }
88 
89  BKE_spacetypes_free(); /* after free main, it uses space callbacks */
90 
91  IMB_exit();
95 
98 
100 
102 
104 }
105 
108 /* -------------------------------------------------------------------- */
112 static char blender_version_string[48] = "";
113 
114 static void blender_version_init(void)
115 {
116  const char *version_cycle = "";
117  if (STREQ(STRINGIFY(BLENDER_VERSION_CYCLE), "alpha")) {
118  version_cycle = " Alpha";
119  }
120  else if (STREQ(STRINGIFY(BLENDER_VERSION_CYCLE), "beta")) {
121  version_cycle = " Beta";
122  }
123  else if (STREQ(STRINGIFY(BLENDER_VERSION_CYCLE), "rc")) {
124  version_cycle = " Release Candidate";
125  }
126  else if (STREQ(STRINGIFY(BLENDER_VERSION_CYCLE), "release")) {
127  version_cycle = "";
128  }
129  else {
130  BLI_assert(!"Invalid Blender version cycle");
131  }
132 
135  "%d.%02d.%d%s",
136  BLENDER_VERSION / 100,
137  BLENDER_VERSION % 100,
139  version_cycle);
140 }
141 
142 const char *BKE_blender_version_string(void)
143 {
144  return blender_version_string;
145 }
146 
148 {
149  bool is_alpha = STREQ(STRINGIFY(BLENDER_VERSION_CYCLE), "alpha");
150  return is_alpha;
151 }
152 
155 /* -------------------------------------------------------------------- */
160 {
162 
163  memset(&G, 0, sizeof(Global));
164 
165  U.savetime = 1;
166 
167  G_MAIN = BKE_main_new();
168 
169  strcpy(G.ima, "//");
170 
171 #ifndef WITH_PYTHON_SECURITY /* default */
173 #else
175 #endif
176 
177  G.log.level = 1;
178 }
179 
181 {
182  BKE_main_free(G_MAIN); /* free all lib data */
183 
184  G_MAIN = NULL;
185 }
186 
189 /* -------------------------------------------------------------------- */
194 {
195  if (kmi->properties) {
197  }
198  if (kmi->ptr) {
199  MEM_freeN(kmi->ptr);
200  }
201 }
202 
203 void BKE_blender_userdef_data_swap(UserDef *userdef_a, UserDef *userdef_b)
204 {
205  SWAP(UserDef, *userdef_a, *userdef_b);
206 }
207 
209 {
210  BKE_blender_userdef_data_swap(&U, userdef);
211  BKE_blender_userdef_data_free(userdef, true);
212 }
213 
215 {
217  MEM_freeN(userdef);
218 }
219 
220 static void userdef_free_keymaps(UserDef *userdef)
221 {
222  for (wmKeyMap *km = userdef->user_keymaps.first, *km_next; km; km = km_next) {
223  km_next = km->next;
224  LISTBASE_FOREACH (wmKeyMapDiffItem *, kmdi, &km->diff_items) {
225  if (kmdi->add_item) {
226  keymap_item_free(kmdi->add_item);
227  MEM_freeN(kmdi->add_item);
228  }
229  if (kmdi->remove_item) {
230  keymap_item_free(kmdi->remove_item);
231  MEM_freeN(kmdi->remove_item);
232  }
233  }
234 
235  LISTBASE_FOREACH (wmKeyMapItem *, kmi, &km->items) {
236  keymap_item_free(kmi);
237  }
238 
239  BLI_freelistN(&km->diff_items);
240  BLI_freelistN(&km->items);
241 
242  MEM_freeN(km);
243  }
244  BLI_listbase_clear(&userdef->user_keymaps);
245 }
246 
248 {
249  for (wmKeyConfigPref *kpt = userdef->user_keyconfig_prefs.first, *kpt_next; kpt;
250  kpt = kpt_next) {
251  kpt_next = kpt->next;
252  IDP_FreeProperty(kpt->prop);
253  MEM_freeN(kpt);
254  }
256 }
257 
258 static void userdef_free_user_menus(UserDef *userdef)
259 {
260  for (bUserMenu *um = userdef->user_menus.first, *um_next; um; um = um_next) {
261  um_next = um->next;
263  MEM_freeN(um);
264  }
265 }
266 
267 static void userdef_free_addons(UserDef *userdef)
268 {
269  for (bAddon *addon = userdef->addons.first, *addon_next; addon; addon = addon_next) {
270  addon_next = addon->next;
271  BKE_addon_free(addon);
272  }
273  BLI_listbase_clear(&userdef->addons);
274 }
275 
280 void BKE_blender_userdef_data_free(UserDef *userdef, bool clear_fonts)
281 {
282 #define U BLI_STATIC_ASSERT(false, "Global 'U' not allowed, only use arguments passed in!")
283 #ifdef U /* quiet warning */
284 #endif
285 
286  userdef_free_keymaps(userdef);
288  userdef_free_user_menus(userdef);
289  userdef_free_addons(userdef);
290 
291  if (clear_fonts) {
292  LISTBASE_FOREACH (uiFont *, font, &userdef->uifonts) {
293  BLF_unload_id(font->blf_id);
294  }
295  BLF_default_set(-1);
296  }
297 
298  BLI_freelistN(&userdef->autoexec_paths);
299  BLI_freelistN(&userdef->asset_libraries);
300 
301  BLI_freelistN(&userdef->uistyles);
302  BLI_freelistN(&userdef->uifonts);
303  BLI_freelistN(&userdef->themes);
304 
305 #undef U
306 }
307 
310 /* -------------------------------------------------------------------- */
319 {
320  /* TODO:
321  * - various minor settings (add as needed).
322  */
323 
324 #define DATA_SWAP(id) \
325  { \
326  UserDef userdef_tmp; \
327  memcpy(&(userdef_tmp.id), &(userdef_a->id), sizeof(userdef_tmp.id)); \
328  memcpy(&(userdef_a->id), &(userdef_b->id), sizeof(userdef_tmp.id)); \
329  memcpy(&(userdef_b->id), &(userdef_tmp.id), sizeof(userdef_tmp.id)); \
330  } \
331  ((void)0)
332 
333 #define LIST_SWAP(id) \
334  { \
335  SWAP(ListBase, userdef_a->id, userdef_b->id); \
336  } \
337  ((void)0)
338 
339 #define FLAG_SWAP(id, ty, flags) \
340  { \
341  CHECK_TYPE(&(userdef_a->id), ty *); \
342  const ty f = flags; \
343  const ty a = userdef_a->id; \
344  const ty b = userdef_b->id; \
345  userdef_a->id = (userdef_a->id & ~f) | (b & f); \
346  userdef_b->id = (userdef_b->id & ~f) | (a & f); \
347  } \
348  ((void)0)
349 
350  LIST_SWAP(uistyles);
351  LIST_SWAP(uifonts);
352  LIST_SWAP(themes);
353  LIST_SWAP(addons);
354  LIST_SWAP(user_keymaps);
355  LIST_SWAP(user_keyconfig_prefs);
356 
357  DATA_SWAP(font_path_ui);
358  DATA_SWAP(font_path_ui_mono);
359  DATA_SWAP(keyconfigstr);
360 
361  DATA_SWAP(gizmo_flag);
362  DATA_SWAP(app_flag);
363 
364  /* We could add others. */
365  FLAG_SWAP(uiflag, int, USER_SAVE_PROMPT);
366 
367 #undef SWAP_TYPELESS
368 #undef DATA_SWAP
369 #undef LIST_SWAP
370 #undef FLAG_SWAP
371 }
372 
374 {
376  BKE_blender_userdef_data_free(userdef, true);
377 }
378 
380 {
382  MEM_freeN(userdef);
383 }
384 
387 /* -------------------------------------------------------------------- */
393 static struct AtExitData {
394  struct AtExitData *next;
395 
396  void (*func)(void *user_data);
397  void *user_data;
399 
401 {
402  struct AtExitData *ae = malloc(sizeof(*ae));
403  ae->next = g_atexit;
404  ae->func = func;
405  ae->user_data = user_data;
406  g_atexit = ae;
407 }
408 
409 void BKE_blender_atexit_unregister(void (*func)(void *user_data), const void *user_data)
410 {
411  struct AtExitData *ae = g_atexit;
412  struct AtExitData **ae_p = &g_atexit;
413 
414  while (ae) {
415  if ((ae->func == func) && (ae->user_data == user_data)) {
416  *ae_p = ae->next;
417  free(ae);
418  return;
419  }
420  ae_p = &ae->next;
421  ae = ae->next;
422  }
423 }
424 
426 {
427  struct AtExitData *ae = g_atexit, *ae_next;
428  while (ae) {
429  ae_next = ae->next;
430 
431  ae->func(ae->user_data);
432 
433  free(ae);
434  ae = ae_next;
435  }
436  g_atexit = NULL;
437 }
438 
void BKE_addon_free(struct bAddon *addon)
Definition: addon.c:80
Blender util stuff.
void BKE_blender_user_menu_item_free_list(struct ListBase *lb)
#define BLENDER_VERSION_PATCH
#define BLENDER_VERSION_CYCLE
#define BLENDER_VERSION
void BKE_brush_system_exit(void)
Definition: brush.c:426
void BKE_cachefiles_exit(void)
Definition: cachefile.c:159
void BKE_callback_global_finalize(void)
Definition: callbacks.c:89
#define G_MAIN
Definition: BKE_global.h:232
@ G_FLAG_SCRIPT_AUTOEXEC
Definition: BKE_global.h:116
void IDP_FreeProperty(struct IDProperty *prop)
Definition: idprop.c:1040
void BKE_images_exit(void)
Definition: image.c:436
struct Main * BKE_main_new(void)
Definition: main.c:45
void BKE_main_free(struct Main *mainvar)
Definition: main.c:53
void BKE_node_system_exit(void)
Definition: node.cc:5030
void BKE_spacetypes_free(void)
Definition: screen.c:373
void BKE_studiolight_free(void)
Definition: studiolight.c:1450
void BLF_default_set(int fontid)
Definition: blf_default.c:48
void BLF_unload_id(int fontid)
Definition: blf.c:260
#define BLI_assert(a)
Definition: BLI_assert.h:58
void BLI_kdtree_nd_() free(KDTree *tree)
Definition: kdtree_impl.h:116
#define LISTBASE_FOREACH(type, var, list)
Definition: BLI_listbase.h:172
BLI_INLINE void BLI_listbase_clear(struct ListBase *lb)
Definition: BLI_listbase.h:128
void void BLI_freelistN(struct ListBase *listbase) ATTR_NONNULL(1)
Definition: listbase.c:547
size_t BLI_snprintf(char *__restrict dst, size_t maxncpy, const char *__restrict format,...) ATTR_NONNULL(1
#define ARRAY_SIZE(arr)
#define SWAP(type, a, b)
#define STRINGIFY(x)
#define STREQ(a, b)
void DEG_free_node_types(void)
@ USER_SAVE_PROMPT
void IMB_exit(void)
Definition: module.c:39
void IMB_moviecache_destruct(void)
Definition: moviecache.c:255
Read Guarded memory(de)allocation.
static struct AtExitData * g_atexit
void BKE_blender_userdef_data_swap(UserDef *userdef_a, UserDef *userdef_b)
Definition: blender.c:203
static char blender_version_string[48]
Definition: blender.c:112
bool BKE_blender_version_is_alpha(void)
Definition: blender.c:147
static void userdef_free_keymaps(UserDef *userdef)
Definition: blender.c:220
void BKE_blender_userdef_data_set(UserDef *userdef)
Definition: blender.c:208
static void userdef_free_addons(UserDef *userdef)
Definition: blender.c:267
void BKE_blender_globals_clear(void)
Definition: blender.c:180
static void userdef_free_user_menus(UserDef *userdef)
Definition: blender.c:258
void BKE_blender_userdef_app_template_data_set_and_free(UserDef *userdef)
Definition: blender.c:379
void BKE_blender_atexit_register(void(*func)(void *user_data), void *user_data)
Definition: blender.c:400
#define DATA_SWAP(id)
void BKE_blender_atexit_unregister(void(*func)(void *user_data), const void *user_data)
Definition: blender.c:409
void BKE_blender_userdef_data_set_and_free(UserDef *userdef)
Definition: blender.c:214
#define LIST_SWAP(id)
void BKE_blender_userdef_app_template_data_set(UserDef *userdef)
Definition: blender.c:373
#define FLAG_SWAP(id, ty, flags)
void BKE_blender_atexit(void)
Definition: blender.c:425
void BKE_blender_userdef_app_template_data_swap(UserDef *userdef_a, UserDef *userdef_b)
Definition: blender.c:318
void BKE_blender_userdef_data_free(UserDef *userdef, bool clear_fonts)
Definition: blender.c:280
Global G
Definition: blender.c:67
void BKE_blender_globals_init(void)
Definition: blender.c:159
static void keymap_item_free(wmKeyMapItem *kmi)
Definition: blender.c:193
void BKE_blender_free(void)
Definition: blender.c:75
const char * BKE_blender_version_string(void)
Definition: blender.c:142
static void blender_version_init(void)
Definition: blender.c:114
static void userdef_free_keyconfig_prefs(UserDef *userdef)
Definition: blender.c:247
#define U
unsigned int U
Definition: btGjkEpa3.h:78
void * user_data
void(* MEM_freeN)(void *vmemh)
Definition: mallocn.c:41
struct AtExitData * next
Definition: blender.c:394
void * user_data
Definition: blender.c:397
void(* func)(void *user_data)
Definition: blender.c:396
int f
Definition: BKE_global.h:87
struct Global::@24 log
void * file
Definition: BKE_global.h:93
int level
Definition: BKE_global.h:91
char ima[1024]
Definition: BKE_global.h:44
void * first
Definition: DNA_listBase.h:47
struct ListBase addons
struct ListBase uistyles
struct ListBase user_keymaps
struct ListBase themes
struct ListBase autoexec_paths
struct ListBase uifonts
struct ListBase user_keyconfig_prefs
struct ListBase user_menus
struct ListBase asset_libraries
struct PointerRNA * ptr
void RE_texture_rng_exit(void)