Merge pull request #2349 from openmv/common_timing

misc/common: Add timing macros.
This commit is contained in:
Ibrahim Abdelkader 2024-08-03 18:41:00 +02:00 committed by GitHub
commit c99840a39a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
9 changed files with 38 additions and 84 deletions

View File

@ -97,6 +97,11 @@ ifeq ($(FB_ALLOC_STATS), 1)
CFLAGS += -DFB_ALLOC_STATS CFLAGS += -DFB_ALLOC_STATS
endif endif
# Enable timing for some functions.
ifeq ($(PROFILE), 1)
CFLAGS += -DOMV_PROFILE_ENABLE=1
endif
# Include OpenMV board config first to set the port. # Include OpenMV board config first to set the port.
include $(OMV_BOARD_CONFIG_DIR)/omv_boardconfig.mk include $(OMV_BOARD_CONFIG_DIR)/omv_boardconfig.mk

View File

@ -9,6 +9,7 @@
* Common macros. * Common macros.
*/ */
#ifndef __OMV_COMMON_H__ #ifndef __OMV_COMMON_H__
#define __OMV_COMMON_H__
#define OMV_ATTR_ALIGNED(x, a) x __attribute__((aligned(a))) #define OMV_ATTR_ALIGNED(x, a) x __attribute__((aligned(a)))
#define OMV_ATTR_SECTION(x, s) x __attribute__((section(s))) #define OMV_ATTR_SECTION(x, s) x __attribute__((section(s)))
@ -46,4 +47,15 @@
#define OMV_ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0])) #define OMV_ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0]))
#if OMV_PROFILE_ENABLE
#include <stdio.h>
#include "py/mphal.h"
#define OMV_PROFILE_START mp_uint_t omv_profile_ticks_start = mp_hal_ticks_us();
#define OMV_PROFILE_END printf("%s %u us\n", __FUNCTION__, mp_hal_ticks_us() - omv_profile_ticks_start);
#else
#define OMV_PROFILE_START
#define OMV_PROFILE_END
#endif
#endif //__OMV_COMMON_H__ #endif //__OMV_COMMON_H__

View File

@ -2843,6 +2843,7 @@ void imlib_draw_image(image_t *dst_img,
imlib_draw_row_callback_t callback, imlib_draw_row_callback_t callback,
void *callback_arg, void *callback_arg,
void *dst_row_override) { void *dst_row_override) {
OMV_PROFILE_START
int dst_delta_x = 1; // positive direction int dst_delta_x = 1; // positive direction
if (x_scale < 0.f) { if (x_scale < 0.f) {
// flip X // flip X
@ -5517,6 +5518,7 @@ exit_cleanup:
if (&new_src_img == src_img) { if (&new_src_img == src_img) {
fb_free(); fb_free();
} }
OMV_PROFILE_END
} }
#ifdef IMLIB_ENABLE_FLOOD_FILL #ifdef IMLIB_ENABLE_FLOOD_FILL

View File

@ -29,6 +29,7 @@
#include "collections.h" #include "collections.h"
#include "imlib_config.h" #include "imlib_config.h"
#include "omv_boardconfig.h" #include "omv_boardconfig.h"
#include "omv_common.h"
// Enables 38 TensorFlow Lite operators. // Enables 38 TensorFlow Lite operators.
#define IMLIB_TF_DEFAULT (1) #define IMLIB_TF_DEFAULT (1)

View File

@ -16,12 +16,6 @@
#include "py/nlr.h" #include "py/nlr.h"
#include "py/runtime.h" #include "py/runtime.h"
#define TIME_JPEG (0)
#if (TIME_JPEG == 1)
#include "py/mphal.h"
#include <stdio.h>
#endif
#if (OMV_JPEG_CODEC_ENABLE == 0) #if (OMV_JPEG_CODEC_ENABLE == 0)
/* Software JPEG decoder */ /* Software JPEG decoder */
#define FILE_HIGHWATER 1536 #define FILE_HIGHWATER 1536
@ -2847,12 +2841,9 @@ static int DecodeJPEG(JPEGIMAGE *pJPEG) {
} }
void jpeg_decompress(image_t *dst, image_t *src) { void jpeg_decompress(image_t *dst, image_t *src) {
OMV_PROFILE_START
JPEGIMAGE jpg; JPEGIMAGE jpg;
#if (TIME_JPEG == 1)
mp_uint_t start = mp_hal_ticks_ms();
#endif
// Supports decoding baseline JPEGs only. // Supports decoding baseline JPEGs only.
if (!jpeg_is_valid(src)) { if (!jpeg_is_valid(src)) {
mp_raise_msg(&mp_type_OSError, MP_ERROR_TEXT("Non-Baseline JPEGs are not supported.")); mp_raise_msg(&mp_type_OSError, MP_ERROR_TEXT("Non-Baseline JPEGs are not supported."));
@ -2891,8 +2882,6 @@ void jpeg_decompress(image_t *dst, image_t *src) {
mp_raise_msg(&mp_type_OSError, MP_ERROR_TEXT("JPEG decoder failed.")); mp_raise_msg(&mp_type_OSError, MP_ERROR_TEXT("JPEG decoder failed."));
} }
#if (TIME_JPEG == 1) OMV_PROFILE_END
printf("time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
} }
#endif #endif

View File

@ -10,14 +10,8 @@
* Ported from public domain JPEG writer by Jon Olick - http://jonolick.com * Ported from public domain JPEG writer by Jon Olick - http://jonolick.com
* DCT implementation is based on Arai, Agui, and Nakajima's algorithm for scaled DCT. * DCT implementation is based on Arai, Agui, and Nakajima's algorithm for scaled DCT.
*/ */
#include "file_utils.h"
#include "imlib.h" #include "imlib.h"
#include "file_utils.h"
#define TIME_JPEG (0)
#if (TIME_JPEG == 1)
#include <stdio.h>
#include "py/mphal.h"
#endif
// Expand 4 bits to 32 for binary to grayscale - process 4 pixels at a time // Expand 4 bits to 32 for binary to grayscale - process 4 pixels at a time
#if (OMV_JPEG_CODEC_ENABLE == 1) #if (OMV_JPEG_CODEC_ENABLE == 1)
@ -1615,9 +1609,7 @@ static void jpeg_write_headers(jpeg_buf_t *jpeg_buf, int w, int h, int bpp, jpeg
} }
bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_subsampling_t subsampling) { bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_subsampling_t subsampling) {
#if (TIME_JPEG == 1) OMV_PROFILE_START
mp_uint_t start = mp_hal_ticks_ms();
#endif
if (!dst->data) { if (!dst->data) {
uint32_t size = 0; uint32_t size = 0;
@ -1949,10 +1941,7 @@ bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_s
dst->size = jpeg_buf.idx; dst->size = jpeg_buf.idx;
dst->data = jpeg_buf.buf; dst->data = jpeg_buf.buf;
#if (TIME_JPEG == 1) OMV_PROFILE_END
printf("compress time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
return false; return false;
} }

View File

@ -8,17 +8,13 @@
* *
* PNG CODEC * PNG CODEC
*/ */
#include <stdio.h>
#include "imlib.h" #include "imlib.h"
#include "py/mphal.h"
#include "py/runtime.h" #include "py/runtime.h"
#include "file_utils.h" #include "file_utils.h"
#if defined(IMLIB_ENABLE_PNG_ENCODER) || defined(IMLIB_ENABLE_PNG_DECODER) #if defined(IMLIB_ENABLE_PNG_ENCODER) || defined(IMLIB_ENABLE_PNG_DECODER)
#include "lodepng.h" #include "lodepng.h"
#include "umm_malloc.h" #include "umm_malloc.h"
#define TIME_PNG (0)
void *lodepng_malloc(size_t size) { void *lodepng_malloc(size_t size) {
return umm_malloc(size); return umm_malloc(size);
} }
@ -109,9 +105,7 @@ unsigned lodepng_convert_cb(unsigned char *out, const unsigned char *in,
#if defined(IMLIB_ENABLE_PNG_ENCODER) #if defined(IMLIB_ENABLE_PNG_ENCODER)
bool png_compress(image_t *src, image_t *dst) { bool png_compress(image_t *src, image_t *dst) {
#if (TIME_PNG == 1) OMV_PROFILE_START
mp_uint_t start = mp_hal_ticks_ms();
#endif
if (src->is_compressed) { if (src->is_compressed) {
return true; return true;
@ -183,21 +177,14 @@ bool png_compress(image_t *src, image_t *dst) {
// free fb_alloc() memory used for umm_init_x(). // free fb_alloc() memory used for umm_init_x().
fb_free(); // umm_init_x(); fb_free(); // umm_init_x();
} }
OMV_PROFILE_END
#if (TIME_PNG == 1)
printf("time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
return false; return false;
} }
#endif // IMLIB_ENABLE_PNG_ENCODER #endif // IMLIB_ENABLE_PNG_ENCODER
#if defined(IMLIB_ENABLE_PNG_DECODER) #if defined(IMLIB_ENABLE_PNG_DECODER)
void png_decompress(image_t *dst, image_t *src) { void png_decompress(image_t *dst, image_t *src) {
#if (TIME_PNG == 1) OMV_PROFILE_START
mp_uint_t start = mp_hal_ticks_ms();
#endif
umm_init_x(fb_avail()); umm_init_x(fb_avail());
LodePNGState state; LodePNGState state;
@ -239,10 +226,7 @@ void png_decompress(image_t *dst, image_t *src) {
// free fb_alloc() memory used for umm_init_x(). // free fb_alloc() memory used for umm_init_x().
fb_free(); // umm_init_x(); fb_free(); // umm_init_x();
OMV_PROFILE_END
#if (TIME_PNG == 1)
printf("time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
} }
#endif // IMLIB_ENABLE_PNG_DECODER #endif // IMLIB_ENABLE_PNG_DECODER
#endif // IMLIB_ENABLE_PNG_ENCODER || IMLIB_ENABLE_PNG_DECODER #endif // IMLIB_ENABLE_PNG_ENCODER || IMLIB_ENABLE_PNG_DECODER

View File

@ -19,11 +19,6 @@
#include "irq.h" #include "irq.h"
#include "dma_utils.h" #include "dma_utils.h"
#define TIME_JPEG (0)
#if (TIME_JPEG == 1)
#include <stdio.h>
#endif
#define JPEG_CODEC_TIMEOUT (1000) #define JPEG_CODEC_TIMEOUT (1000)
#define JPEG_ALLOC_PADDING ((__SCB_DCACHE_LINE_SIZE) * 4) #define JPEG_ALLOC_PADDING ((__SCB_DCACHE_LINE_SIZE) * 4)
#define JPEG_OUTPUT_CHUNK_SIZE (512) // The minimum output buffer size is 2x this - so 1KB. #define JPEG_OUTPUT_CHUNK_SIZE (512) // The minimum output buffer size is 2x this - so 1KB.
@ -111,10 +106,7 @@ static void jpeg_compress_data_ready(JPEG_HandleTypeDef *hjpeg, uint8_t *pDataOu
} }
bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_subsampling_t subsampling) { bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_subsampling_t subsampling) {
#if (TIME_JPEG == 1) OMV_PROFILE_START
mp_uint_t start = mp_hal_ticks_ms();
#endif
HAL_JPEG_RegisterGetDataCallback(&JPEG_state.jpeg_descr, jpeg_compress_get_data); HAL_JPEG_RegisterGetDataCallback(&JPEG_state.jpeg_descr, jpeg_compress_get_data);
HAL_JPEG_RegisterDataReadyCallback(&JPEG_state.jpeg_descr, jpeg_compress_data_ready); HAL_JPEG_RegisterDataReadyCallback(&JPEG_state.jpeg_descr, jpeg_compress_data_ready);
@ -365,12 +357,7 @@ bool jpeg_compress(image_t *src, image_t *dst, int quality, bool realloc, jpeg_s
// Clean trailing data after 0xFFD9 at the end of the jpeg byte stream. // Clean trailing data after 0xFFD9 at the end of the jpeg byte stream.
dst->size = jpeg_clean_trailing_bytes(dst->size, dst->data); dst->size = jpeg_clean_trailing_bytes(dst->size, dst->data);
#if (TIME_JPEG == 1)
printf("compress time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
exit_cleanup: exit_cleanup:
// Cleanup jpeg state. // Cleanup jpeg state.
HAL_JPEG_Abort(&JPEG_state.jpeg_descr); HAL_JPEG_Abort(&JPEG_state.jpeg_descr);
HAL_JPEG_UnRegisterDataReadyCallback(&JPEG_state.jpeg_descr); HAL_JPEG_UnRegisterDataReadyCallback(&JPEG_state.jpeg_descr);
@ -378,6 +365,7 @@ exit_cleanup:
fb_free(); // mcu_row_buffer (after DMA is aborted) fb_free(); // mcu_row_buffer (after DMA is aborted)
OMV_PROFILE_END
return jpeg_overflow; return jpeg_overflow;
} }
@ -409,9 +397,7 @@ static void jpeg_decompress_data_ready(JPEG_HandleTypeDef *hjpeg, uint8_t *pData
} }
void jpeg_decompress(image_t *dst, image_t *src) { void jpeg_decompress(image_t *dst, image_t *src) {
#if (TIME_JPEG == 1) OMV_PROFILE_START
mp_uint_t start = mp_hal_ticks_ms();
#endif
// Verify the jpeg image is not a non-baseline jpeg image and check that is has // Verify the jpeg image is not a non-baseline jpeg image and check that is has
// valid headers up to the start-of-scan header (which cannot be trivially walked). // valid headers up to the start-of-scan header (which cannot be trivially walked).
@ -749,10 +735,6 @@ void jpeg_decompress(image_t *dst, image_t *src) {
} }
} }
#if (TIME_JPEG == 1)
printf("decompress time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
exit_cleanup: exit_cleanup:
// Cleanup jpeg state. // Cleanup jpeg state.
@ -769,6 +751,8 @@ exit_cleanup:
if (((uint32_t) src->data) % __SCB_DCACHE_LINE_SIZE) { if (((uint32_t) src->data) % __SCB_DCACHE_LINE_SIZE) {
fb_free(); // JPEG_state.jpeg_descr.pJpegInBuffPtr (after DMA is aborted) fb_free(); // JPEG_state.jpeg_descr.pJpegInBuffPtr (after DMA is aborted)
} }
OMV_PROFILE_END
} }
void imlib_hardware_jpeg_init() { void imlib_hardware_jpeg_init() {

View File

@ -10,17 +10,10 @@
*/ */
#include "omv_boardconfig.h" #include "omv_boardconfig.h"
#if (OMV_GPU_ENABLE == 1) #if (OMV_GPU_ENABLE == 1)
#include "imlib.h"
#include STM32_HAL_H #include STM32_HAL_H
#include "imlib.h"
#include "dma.h" #include "dma.h"
#define TIME_GPU (0)
#if (TIME_GPU == 1)
#include "py/mphal.h"
#include <stdio.h>
#endif
int omv_gpu_init() { int omv_gpu_init() {
return 0; return 0;
} }
@ -39,6 +32,8 @@ int omv_gpu_draw_image(image_t *src_img,
const uint16_t *color_palette, const uint16_t *color_palette,
const uint8_t *alpha_palette, const uint8_t *alpha_palette,
image_hint_t hint) { image_hint_t hint) {
OMV_PROFILE_START
// DMA2D can only draw on RGB565 buffers and the destination/source buffers must be accessible by DMA. // DMA2D can only draw on RGB565 buffers and the destination/source buffers must be accessible by DMA.
if ((dst_img->pixfmt != PIXFORMAT_RGB565) || (!DMA_BUFFER(dst_img->data)) || (!DMA_BUFFER(src_img->data))) { if ((dst_img->pixfmt != PIXFORMAT_RGB565) || (!DMA_BUFFER(dst_img->data)) || (!DMA_BUFFER(src_img->data))) {
return -1; return -1;
@ -69,10 +64,6 @@ int omv_gpu_draw_image(image_t *src_img,
} }
#endif #endif
#if (TIME_GPU == 1)
mp_uint_t start = mp_hal_ticks_ms();
#endif
DMA2D_HandleTypeDef dma2d = {}; DMA2D_HandleTypeDef dma2d = {};
dma2d.Instance = DMA2D; dma2d.Instance = DMA2D;
@ -220,10 +211,7 @@ int omv_gpu_draw_image(image_t *src_img,
fb_free(); // clut fb_free(); // clut
} }
#if (TIME_GPU == 1) OMV_PROFILE_END
printf("draw time: %u ms\n", mp_hal_ticks_ms() - start);
#endif
return 0; return 0;
} }
#endif // (OMV_GPU_ENABLE == 1) #endif // (OMV_GPU_ENABLE == 1)