Skip to content

Commit e689c3b

Browse files
authored
Support: jpeg decoder on esp32c2 (#525)
* Extend s/w jpeg decoder functions for chips missing rom tjpgd Also, disabled camera_init and capture from example for chips not supporting camera Signed-off-by: Vikram <[email protected]> * Extend CI build support for C3 and C2 Signed-off-by: Vikram <[email protected]> --------- Signed-off-by: Vikram <[email protected]>
1 parent 36b8b4e commit e689c3b

File tree

8 files changed

+141
-17
lines changed

8 files changed

+141
-17
lines changed

.github/workflows/build.yml

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,10 @@ jobs:
3535
strategy:
3636
matrix:
3737
idf_ver: ["release-v4.4", "release-v5.0", "release-v5.1", "latest"]
38-
idf_target: ["esp32", "esp32s2", "esp32s3"]
38+
idf_target: ["esp32", "esp32s2", "esp32s3", "esp32c2", "esp32c3"]
39+
exclude:
40+
- idf_ver: "release-v4.4"
41+
idf_target: esp32c2 # ESP32C2 support started with version 5.0
3942
container: espressif/idf:${{ matrix.idf_ver }}
4043
steps:
4144
- uses: actions/checkout@v1

CMakeLists.txt

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ if(IDF_TARGET STREQUAL "esp32" OR IDF_TARGET STREQUAL "esp32s2" OR IDF_TARGET ST
6161
list(APPEND COMPONENT_SRCS
6262
target/xclk.c
6363
target/esp32s2/ll_cam.c
64-
target/esp32s2/tjpgd.c
64+
target/tjpgd.c
6565
)
6666

6767
list(APPEND COMPONENT_PRIV_INCLUDEDIRS
@@ -84,4 +84,15 @@ if(IDF_TARGET STREQUAL "esp32" OR IDF_TARGET STREQUAL "esp32s2" OR IDF_TARGET ST
8484

8585
endif()
8686

87+
# CONFIG_ESP_ROM_HAS_JPEG_DECODE is available from IDF v4.4 but
88+
# previous IDF supported chips already support JPEG decoder, hence okay to use this
89+
if(idf_version VERSION_GREATER_EQUAL "4.4" AND NOT CONFIG_ESP_ROM_HAS_JPEG_DECODE)
90+
list(APPEND COMPONENT_SRCS
91+
target/tjpgd.c
92+
)
93+
list(APPEND COMPONENT_PRIV_INCLUDEDIRS
94+
target/jpeg_include/
95+
)
96+
endif()
97+
8798
register_component()

conversions/esp_jpg_decode.c

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,16 +17,14 @@
1717
#if ESP_IDF_VERSION_MAJOR >= 4 // IDF 4+
1818
#if CONFIG_IDF_TARGET_ESP32 // ESP32/PICO-D4
1919
#include "esp32/rom/tjpgd.h"
20-
#elif CONFIG_IDF_TARGET_ESP32S2
21-
#include "tjpgd.h"
2220
#elif CONFIG_IDF_TARGET_ESP32S3
2321
#include "esp32s3/rom/tjpgd.h"
2422
#elif CONFIG_IDF_TARGET_ESP32C3
2523
#include "esp32c3/rom/tjpgd.h"
26-
#elif CONFIG_IDF_TARGET_ESP32H2
27-
#include "esp32h2/rom/tjpgd.h"
24+
#elif CONFIG_ESP_ROM_HAS_JPEG_DECODE // available since IDF 4.4
25+
#include "rom/tjpgd.h" // latest IDFs have `rom/` includes available
2826
#else
29-
#error Target CONFIG_IDF_TARGET is not supported
27+
#include "tjpgd.h" // using software decoder
3028
#endif
3129
#else // ESP32 Before IDF 4.0
3230
#include "rom/tjpgd.h"

driver/esp_camera.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -245,7 +245,7 @@ static esp_err_t camera_probe(const camera_config_t *config, camera_model_t *out
245245

246246
ESP_LOGD(TAG, "Doing SW reset of sensor");
247247
vTaskDelay(10 / portTICK_PERIOD_MS);
248-
248+
249249
return s_state->sensor.reset(&s_state->sensor);
250250
err :
251251
CAMERA_DISABLE_OUT_CLOCK();

driver/include/esp_camera.h

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,12 @@
7272
#include "sys/time.h"
7373
#include "sdkconfig.h"
7474

75+
/**
76+
* @brief define for if chip supports camera
77+
*/
78+
#define ESP_CAMERA_SUPPORTED (CONFIG_IDF_TARGET_ESP32 | CONFIG_IDF_TARGET_ESP32S3 | \
79+
CONFIG_IDF_TARGET_ESP32S2)
80+
7581
#ifdef __cplusplus
7682
extern "C" {
7783
#endif
@@ -85,7 +91,7 @@ typedef enum {
8591
} camera_grab_mode_t;
8692

8793
/**
88-
* @brief Camera frame buffer location
94+
* @brief Camera frame buffer location
8995
*/
9096
typedef enum {
9197
CAMERA_FB_IN_PSRAM, /*!< Frame buffer is placed in external PSRAM */
@@ -99,7 +105,7 @@ typedef enum {
99105
typedef enum {
100106
CONV_DISABLE,
101107
RGB565_TO_YUV422,
102-
108+
103109
YUV422_TO_RGB565,
104110
YUV422_TO_YUV420
105111
} camera_conv_mode_t;
@@ -219,15 +225,15 @@ sensor_t * esp_camera_sensor_get(void);
219225

220226
/**
221227
* @brief Save camera settings to non-volatile-storage (NVS)
222-
*
223-
* @param key A unique nvs key name for the camera settings
228+
*
229+
* @param key A unique nvs key name for the camera settings
224230
*/
225231
esp_err_t esp_camera_save_to_nvs(const char *key);
226232

227233
/**
228234
* @brief Load camera settings from non-volatile-storage (NVS)
229-
*
230-
* @param key A unique nvs key name for the camera settings
235+
*
236+
* @param key A unique nvs key name for the camera settings
231237
*/
232238
esp_err_t esp_camera_load_from_nvs(const char *key);
233239

examples/main/take_picture.c

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010

1111
/**
1212
* 2. Kconfig setup
13-
*
13+
*
1414
* If you have a Kconfig file, copy the content from
1515
* https://github.com/espressif/esp32-camera/blob/master/Kconfig into it.
1616
* In case you haven't, copy and paste this Kconfig file inside the src directory.
@@ -20,9 +20,9 @@
2020

2121
/**
2222
* 3. Enable PSRAM on sdkconfig:
23-
*
23+
*
2424
* CONFIG_ESP32_SPIRAM_SUPPORT=y
25-
*
25+
*
2626
* More info on
2727
* https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-reference/kconfig.html#config-esp32-spiram-support
2828
*/
@@ -95,6 +95,7 @@
9595

9696
static const char *TAG = "example:take_picture";
9797

98+
#if ESP_CAMERA_SUPPORTED
9899
static camera_config_t camera_config = {
99100
.pin_pwdn = CAM_PIN_PWDN,
100101
.pin_reset = CAM_PIN_RESET,
@@ -139,9 +140,11 @@ static esp_err_t init_camera(void)
139140

140141
return ESP_OK;
141142
}
143+
#endif
142144

143145
void app_main(void)
144146
{
147+
#if ESP_CAMERA_SUPPORTED
145148
if(ESP_OK != init_camera()) {
146149
return;
147150
}
@@ -157,4 +160,8 @@ void app_main(void)
157160

158161
vTaskDelay(5000 / portTICK_RATE_MS);
159162
}
163+
#else
164+
ESP_LOGE(TAG, "Camera support is not available for this chip");
165+
return;
166+
#endif
160167
}

target/jpeg_include/tjpgd.h

Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
1+
/*----------------------------------------------------------------------------/
2+
/ TJpgDec - Tiny JPEG Decompressor include file (C)ChaN, 2012
3+
/----------------------------------------------------------------------------*/
4+
#ifndef _TJPGDEC
5+
#define _TJPGDEC
6+
/*---------------------------------------------------------------------------*/
7+
/* System Configurations */
8+
9+
#define JD_SZBUF 512 /* Size of stream input buffer */
10+
#define JD_FORMAT 0 /* Output pixel format 0:RGB888 (3 BYTE/pix), 1:RGB565 (1 WORD/pix) */
11+
#define JD_USE_SCALE 1 /* Use descaling feature for output */
12+
#define JD_TBLCLIP 1 /* Use table for saturation (might be a bit faster but increases 1K bytes of code size) */
13+
14+
/*---------------------------------------------------------------------------*/
15+
16+
#ifdef __cplusplus
17+
extern "C" {
18+
#endif
19+
20+
/* These types must be 16-bit, 32-bit or larger integer */
21+
typedef int INT;
22+
typedef unsigned int UINT;
23+
24+
/* These types must be 8-bit integer */
25+
typedef char CHAR;
26+
typedef unsigned char UCHAR;
27+
typedef unsigned char BYTE;
28+
29+
/* These types must be 16-bit integer */
30+
typedef short SHORT;
31+
typedef unsigned short USHORT;
32+
typedef unsigned short WORD;
33+
typedef unsigned short WCHAR;
34+
35+
/* These types must be 32-bit integer */
36+
typedef long LONG;
37+
typedef unsigned long ULONG;
38+
typedef unsigned long DWORD;
39+
40+
41+
/* Error code */
42+
typedef enum {
43+
JDR_OK = 0, /* 0: Succeeded */
44+
JDR_INTR, /* 1: Interrupted by output function */
45+
JDR_INP, /* 2: Device error or wrong termination of input stream */
46+
JDR_MEM1, /* 3: Insufficient memory pool for the image */
47+
JDR_MEM2, /* 4: Insufficient stream input buffer */
48+
JDR_PAR, /* 5: Parameter error */
49+
JDR_FMT1, /* 6: Data format error (may be damaged data) */
50+
JDR_FMT2, /* 7: Right format but not supported */
51+
JDR_FMT3 /* 8: Not supported JPEG standard */
52+
} JRESULT;
53+
54+
55+
56+
/* Rectangular structure */
57+
typedef struct {
58+
WORD left, right, top, bottom;
59+
} JRECT;
60+
61+
62+
63+
/* Decompressor object structure */
64+
typedef struct JDEC JDEC;
65+
struct JDEC {
66+
UINT dctr; /* Number of bytes available in the input buffer */
67+
BYTE* dptr; /* Current data read ptr */
68+
BYTE* inbuf; /* Bit stream input buffer */
69+
BYTE dmsk; /* Current bit in the current read byte */
70+
BYTE scale; /* Output scaling ratio */
71+
BYTE msx, msy; /* MCU size in unit of block (width, height) */
72+
BYTE qtid[3]; /* Quantization table ID of each component */
73+
SHORT dcv[3]; /* Previous DC element of each component */
74+
WORD nrst; /* Restart inverval */
75+
UINT width, height; /* Size of the input image (pixel) */
76+
BYTE* huffbits[2][2]; /* Huffman bit distribution tables [id][dcac] */
77+
WORD* huffcode[2][2]; /* Huffman code word tables [id][dcac] */
78+
BYTE* huffdata[2][2]; /* Huffman decoded data tables [id][dcac] */
79+
LONG* qttbl[4]; /* Dequaitizer tables [id] */
80+
void* workbuf; /* Working buffer for IDCT and RGB output */
81+
BYTE* mcubuf; /* Working buffer for the MCU */
82+
void* pool; /* Pointer to available memory pool */
83+
UINT sz_pool; /* Size of momory pool (bytes available) */
84+
UINT (*infunc)(JDEC*, BYTE*, UINT);/* Pointer to jpeg stream input function */
85+
void* device; /* Pointer to I/O device identifiler for the session */
86+
};
87+
88+
89+
90+
/* TJpgDec API functions */
91+
JRESULT jd_prepare (JDEC*, UINT(*)(JDEC*,BYTE*,UINT), void*, UINT, void*);
92+
JRESULT jd_decomp (JDEC*, UINT(*)(JDEC*,void*,JRECT*), BYTE);
93+
94+
95+
#ifdef __cplusplus
96+
}
97+
#endif
98+
99+
#endif /* _TJPGDEC */
File renamed without changes.

0 commit comments

Comments
 (0)