Subsurf: Add basic statistics to help benchmarking
This commit is contained in:
parent
94722121e5
commit
8a42b3909f
Notes:
blender-bot
2023-02-14 05:33:50 +01:00
Referenced by issue #56016, Working with curves crashes Blender 2.8
|
@ -53,6 +53,40 @@ typedef struct SubdivSettings {
|
|||
eSubdivFVarLinearInterpolation fvar_linear_interpolation;
|
||||
} SubdivSettings;
|
||||
|
||||
/* NOTE: Order of enumerators MUST match order of values in SubdivStats. */
|
||||
typedef enum eSubdivStatsValue {
|
||||
SUBDIV_STATS_TOPOLOGY_REFINER_CREATION_TIME = 0,
|
||||
SUBDIV_STATS_SUBDIV_TO_MESH,
|
||||
SUBDIV_STATS_EVALUATOR_CREATE,
|
||||
SUBDIV_STATS_EVALUATOR_REFINE,
|
||||
|
||||
NUM_SUBDIV_STATS_VALUES,
|
||||
} eSubdivStatsValue;
|
||||
|
||||
typedef struct SubdivStats {
|
||||
union {
|
||||
struct {
|
||||
/* Time spend on creating topology refiner, which includes time
|
||||
* spend on conversion from Blender data to OpenSubdiv data, and
|
||||
* time spend on topology orientation on OpenSubdiv C-API side.
|
||||
*/
|
||||
double topology_refiner_creation_time;
|
||||
/* Total time spent in BKE_subdiv_to_mesh(). */
|
||||
double subdiv_to_mesh_time;
|
||||
/* Time spent on evaluator creation from topology refiner. */
|
||||
double evaluator_creation_time;
|
||||
/* Time spent on evaluator->refine(). */
|
||||
double evaluator_refine_time;
|
||||
};
|
||||
double values_[NUM_SUBDIV_STATS_VALUES];
|
||||
};
|
||||
|
||||
/* Per-value timestamp on when corresponding BKE_subdiv_stats_begin() was
|
||||
* called.
|
||||
*/
|
||||
double begin_timestamp_[NUM_SUBDIV_STATS_VALUES];
|
||||
} SubdivStats;
|
||||
|
||||
typedef struct Subdiv {
|
||||
/* Settings this subdivision surface is created for.
|
||||
*
|
||||
|
@ -88,8 +122,19 @@ typedef struct Subdiv {
|
|||
|
||||
/* CPU side evaluator. */
|
||||
struct OpenSubdiv_Evaluator *evaluator;
|
||||
|
||||
SubdivStats stats;
|
||||
} Subdiv;
|
||||
|
||||
/* =============================== STATISTICS =============================== */
|
||||
|
||||
void BKE_subdiv_stats_init(SubdivStats *stats);
|
||||
|
||||
void BKE_subdiv_stats_begin(SubdivStats *stats, eSubdivStatsValue value);
|
||||
void BKE_subdiv_stats_end(SubdivStats *stats, eSubdivStatsValue value);
|
||||
|
||||
void BKE_subdiv_stats_print(const SubdivStats *stats);
|
||||
|
||||
/* ============================== CONSTRUCTION ============================== */
|
||||
|
||||
Subdiv *BKE_subdiv_new_from_converter(const SubdivSettings *settings,
|
||||
|
|
|
@ -191,6 +191,7 @@ set(SRC
|
|||
intern/subdiv_converter_mesh.c
|
||||
intern/subdiv_eval.c
|
||||
intern/subdiv_mesh.c
|
||||
intern/subdiv_stats.c
|
||||
intern/subsurf_ccg.c
|
||||
intern/suggestions.c
|
||||
intern/text.c
|
||||
|
|
|
@ -63,6 +63,9 @@ Subdiv *BKE_subdiv_new_from_converter(const SubdivSettings *settings,
|
|||
struct OpenSubdiv_Converter *converter)
|
||||
{
|
||||
#ifdef WITH_OPENSUBDIV
|
||||
SubdivStats stats;
|
||||
BKE_subdiv_stats_init(&stats);
|
||||
BKE_subdiv_stats_begin(&stats, SUBDIV_STATS_TOPOLOGY_REFINER_CREATION_TIME);
|
||||
OpenSubdiv_TopologyRefinerSettings topology_refiner_settings;
|
||||
topology_refiner_settings.level = settings->level;
|
||||
topology_refiner_settings.is_adaptive = settings->is_adaptive;
|
||||
|
@ -77,6 +80,8 @@ Subdiv *BKE_subdiv_new_from_converter(const SubdivSettings *settings,
|
|||
subdiv->topology_refiner = osd_topology_refiner;
|
||||
subdiv->evaluator = NULL;
|
||||
update_subdiv_after_topology_change(subdiv);
|
||||
BKE_subdiv_stats_end(&stats, SUBDIV_STATS_TOPOLOGY_REFINER_CREATION_TIME);
|
||||
subdiv->stats = stats;
|
||||
return subdiv;
|
||||
#else
|
||||
UNUSED_VARS(settings, converter);
|
||||
|
|
|
@ -46,8 +46,10 @@ void BKE_subdiv_eval_begin(Subdiv *subdiv)
|
|||
{
|
||||
#ifdef WITH_OPENSUBDIV
|
||||
if (subdiv->evaluator == NULL) {
|
||||
BKE_subdiv_stats_begin(&subdiv->stats, SUBDIV_STATS_EVALUATOR_CREATE);
|
||||
subdiv->evaluator = openSubdiv_createEvaluatorFromTopologyRefiner(
|
||||
subdiv->topology_refiner);
|
||||
BKE_subdiv_stats_end(&subdiv->stats, SUBDIV_STATS_EVALUATOR_CREATE);
|
||||
}
|
||||
else {
|
||||
/* TODO(sergey): Check for topology change. */
|
||||
|
@ -112,7 +114,9 @@ void BKE_subdiv_eval_update_from_mesh(Subdiv *subdiv, const Mesh *mesh)
|
|||
break;
|
||||
}
|
||||
/* Update evaluator to the new coarse geometry. */
|
||||
BKE_subdiv_stats_begin(&subdiv->stats, SUBDIV_STATS_EVALUATOR_REFINE);
|
||||
subdiv->evaluator->refine(subdiv->evaluator);
|
||||
BKE_subdiv_stats_end(&subdiv->stats, SUBDIV_STATS_EVALUATOR_REFINE);
|
||||
#else
|
||||
UNUSED_VARS(subdiv, mesh);
|
||||
#endif
|
||||
|
|
|
@ -912,6 +912,7 @@ Mesh *BKE_subdiv_to_mesh(
|
|||
const SubdivToMeshSettings *settings,
|
||||
const Mesh *coarse_mesh)
|
||||
{
|
||||
BKE_subdiv_stats_begin(&subdiv->stats, SUBDIV_STATS_SUBDIV_TO_MESH);
|
||||
/* Make sure evaluator is up to date with possible new topology, and that
|
||||
* is is refined for the new positions of coarse vertices.
|
||||
*/
|
||||
|
@ -946,5 +947,6 @@ Mesh *BKE_subdiv_to_mesh(
|
|||
&ctx,
|
||||
subdiv_eval_task,
|
||||
¶llel_range_settings);
|
||||
BKE_subdiv_stats_end(&subdiv->stats, SUBDIV_STATS_SUBDIV_TO_MESH);
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,80 @@
|
|||
/*
|
||||
* ***** BEGIN GPL LICENSE BLOCK *****
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation; either version 2
|
||||
* of the License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*
|
||||
* The Original Code is Copyright (C) 2018 by Blender Foundation.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Contributor(s): Sergey Sharybin.
|
||||
*
|
||||
* ***** END GPL LICENSE BLOCK *****
|
||||
*/
|
||||
|
||||
/** \file blender/blenkernel/intern/subdiv_stats.c
|
||||
* \ingroup bke
|
||||
*/
|
||||
|
||||
#include "BKE_subdiv.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "PIL_time.h"
|
||||
|
||||
void BKE_subdiv_stats_init(SubdivStats *stats)
|
||||
{
|
||||
stats->topology_refiner_creation_time = 0.0;
|
||||
stats->subdiv_to_mesh_time = 0.0;
|
||||
stats->evaluator_creation_time = 0.0;
|
||||
stats->evaluator_refine_time = 0.0;
|
||||
}
|
||||
|
||||
void BKE_subdiv_stats_begin(SubdivStats *stats, eSubdivStatsValue value)
|
||||
{
|
||||
stats->begin_timestamp_[value] = PIL_check_seconds_timer();
|
||||
}
|
||||
|
||||
void BKE_subdiv_stats_end(SubdivStats *stats, eSubdivStatsValue value)
|
||||
{
|
||||
stats->values_[value] =
|
||||
PIL_check_seconds_timer() - stats->begin_timestamp_[value];
|
||||
}
|
||||
|
||||
void BKE_subdiv_stats_print(const SubdivStats *stats)
|
||||
{
|
||||
#define STATS_PRINT_TIME(stats, value, description) \
|
||||
do { \
|
||||
if ((stats)->value > 0.0) { \
|
||||
printf(" %s: %f (sec)\n", description, (stats)->value); \
|
||||
} \
|
||||
} while (false)
|
||||
|
||||
printf("Subdivision surface statistics:\n");
|
||||
|
||||
STATS_PRINT_TIME(stats,
|
||||
topology_refiner_creation_time,
|
||||
"Topology refiner creation time");
|
||||
STATS_PRINT_TIME(stats,
|
||||
subdiv_to_mesh_time,
|
||||
"Subdivision to mesh time");
|
||||
STATS_PRINT_TIME(stats,
|
||||
evaluator_creation_time,
|
||||
"Evaluator creation time");
|
||||
STATS_PRINT_TIME(stats,
|
||||
evaluator_refine_time,
|
||||
"Evaluator refine time");
|
||||
|
||||
#undef STATS_PRINT_TIME
|
||||
}
|
|
@ -247,6 +247,7 @@ static Mesh *applyModifier_subdiv(ModifierData *md,
|
|||
subdiv_mesh_settings_init(&mesh_settings, &subdiv_settings);
|
||||
result = BKE_subdiv_to_mesh(subdiv, &mesh_settings, mesh);
|
||||
/* TODO(sergey): Cache subdiv somehow. */
|
||||
// BKE_subdiv_stats_print(&subdiv->stats);
|
||||
BKE_subdiv_free(subdiv);
|
||||
return result;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue