SDK สำหรับ TESAIoT Dev Kit
คู่มืออ้างอิง API และ Tutorial (MTB & µPython)
Loading...
Searching...
No Matches
การเปิดใช้งานจอแสดงผล

Functions

BaseType_t tesaiot_display_init (void)
 จุดเข้าใช้งานสาธารณะจุดเดียว — สร้าง GFX task ก่อน scheduler เริ่มทำงาน; เทียบค่าที่คืนกลับมากับ pdPASS
void tesaiot_display_task (void *arg)
 ตัวเนื้อของ GFX task — ห้ามสร้างเอง ห้ามเรียกเอง

Variables

volatile uint8_t tesaiot_display_ready
 flag บอกสถานะการเปิดใช้งานแบบ 3 ค่า: 0 ยังไม่เสร็จ, 1 จอแสดงผลและ IPC พร้อม, 2 ขึ้นเฉพาะ IPC แบบ headless

Detailed Description

Header: tesaiot_display.h ตัวโค้ดจริง: tesaiot_display.c ที่อยู่ใน archive (libbento_cm55.a) เป็นเจ้าของการเปิดใช้งาน GFXSS, vg_lite และ LVGL, บัส I2C ของจอแสดงผลและการสัมผัส, GFX task และ — เพราะรัน IPC prologue ก่อนจอแสดงผล — ลำดับการบูตทั้งหมดของ CM55 (ดูคู่มืออ้างอิงของ ipc_core)

variant ที่ใช้ได้
mtb-mpy และ mtb-only

tesaiot_display_ready มี 3 ค่า

0 = ยังไม่เสร็จ, 1 = จอแสดงผลและ IPC ขึ้นแล้ว, 2 = ขึ้นเฉพาะ IPC แบบ headless (พาเนลล้มเหลวแต่เส้นทาง IPC ขึ้นมาได้) ผู้เรียกทั้ง 2 รายที่มีอยู่จริงในของที่ส่งมอบตรวจด้วย == 0 บอร์ดที่เป็น headless จึงเดินต่อไปได้ การตรวจด้วย == 1 จะทำให้ผู้ใช้ไลบรารีค้างอยู่บนบอร์ดที่จอดับ — ซึ่งหลังจากรีเซ็ตด้วยดีบักเกอร์แล้ว บอร์ดทุกตัวเป็นเช่นนั้น

Function Documentation

◆ tesaiot_display_init()

BaseType_t tesaiot_display_init ( void )

จุดเข้าใช้งานสาธารณะจุดเดียว — สร้าง GFX task ก่อน scheduler เริ่มทำงาน; เทียบค่าที่คืนกลับมากับ pdPASS

ข้อกำหนดการเรียกใช้
ลำดับที่ต้องใช้: cybsp_init() แล้ว __enable_irq() แล้วจึงเรียกฟังก์ชันนี้ — ISR (interrupt service routine) ของ DC/GPU ใน GFXSS ถูกต่อสายไว้ระหว่างการเริ่ม task ดังนั้นอินเทอร์รัปต์ต้องเปิดอยู่ก่อน เรียกจาก main() ก่อน vTaskStartScheduler() คือสร้าง GFX task ขึ้นมาเท่านั้น ไม่ได้รันมัน เทียบค่าที่คืนกลับมากับ pdPASS ไม่ใช่ CY_RSLT_SUCCESS เทมเพลตจะล้มเหลวแบบไปต่อไม่ได้ เข้าสู่ลูป LED ที่ต่างกัน (LED1 = cybsp_init ล้มเหลว, LED2 = ฟังก์ชันนี้ล้มเหลว) เพื่อให้แยก 2 กรณีออกจากกันได้ด้วยตา ฟังก์ชันนี้เป็นจุดเข้าใช้งานสาธารณะจุดเดียว คือสร้าง GFX task ด้วย xTaskCreate(tesaiot_display_task, ...) แล้วเก็บ handle ไว้ใน rtos_cm55_gfx_task_handle (tesaiot_display.c:210-213) task ตัวนี้เปิดใช้งาน IPC ก่อนจอแสดงผล เพื่อให้ IPC ยังอยู่รอดแม้จอแสดงผลจะล้มเหลว — ซึ่งเป็นเหตุผลที่ tesaiot_display_ready มีค่า 2 ได้
variant ที่ใช้ได้
mtb-mpy และ mtb-only
int main(void)
{
cy_rslt_t result;
#if TESAIOT_ENABLE_FACE_RUNTIME && TESAIOT_ENABLE_FACE_RUNTIME_BOOT
/* Alternate boot mode: launch native Face-ID runtime. */
if (face_mode_runtime_requested()) {
face_mode_launch_runtime();
}
#endif
/* Initialize the device and board peripherals */
result = cybsp_init();
if (CY_RSLT_SUCCESS != result)
{
for (;;) {
Cy_GPIO_Inv(CYBSP_USER_LED1_PORT, CYBSP_USER_LED1_PIN);
Cy_SysLib_Delay(50);
}
}
/* Enable global interrupts */
__enable_irq();
/* GFX task: GFXSS/LVGL init + IPC + sensorhub UI */
BaseType_t xResult = tesaiot_display_init();
if (pdPASS != xResult) {
for (;;) {
Cy_GPIO_Inv(CYBSP_USER_LED2_PORT, CYBSP_USER_LED2_PIN);
Cy_SysLib_Delay(50);
}
}

◆ tesaiot_display_task()

void tesaiot_display_task ( void * arg)

ตัวเนื้อของ GFX task — ห้ามสร้างเอง ห้ามเรียกเอง

ข้อกำหนดการเรียกใช้
ตัวเนื้อของ GFX task ถูกอ้างถึงเฉพาะในฐานะอาร์กิวเมนต์ของ xTaskCreate ภายใน tesaiot_display_init() (tesaiot_display.c:211) เท่านั้น anti-example: ห้ามสร้างมันขึ้นมาเอง ห้ามเรียกมันเอง — GFX task ตัวที่ 2 หมายถึงมีเจ้าของ LVGL 2 ราย มี IPC prologue 2 ชุด และมีการเรียก cm55_ipc_communication_setup() ซ้ำ 2 ครั้ง ผู้ใช้ไลบรารีเรียก tesaiot_display_init() เท่านั้น ไม่เรียกอย่างอื่น
variant ที่ใช้ได้
mtb-mpy และ mtb-only
ตัวอย่าง (เขียนขึ้นเอง — ไม่มี call site ในของที่ส่งมอบจริง)
/* Hand-written externs matching dist/cm55_core/include/tesaiot_display.h
* (included here as declarations only, to keep the example free of that
* header's display include chain): */
extern BaseType_t tesaiot_display_init(void);
extern void tesaiot_display_task(void *arg);
static void bento_ex_tesaiot_display_task(void)
{
/* WRONG:
* xTaskCreate(tesaiot_display_task, "gfx2", 4096, NULL, 1, NULL);
* tesaiot_display_task(NULL); // never returns, no init
*
* RIGHT — the one public entry, from main() pre-scheduler: */
if (tesaiot_display_init() != pdPASS) { /* pdPASS, not CY_RSLT_* */
/* distinct LED failure loop in shipped main(); do not continue
* into vTaskStartScheduler() pretending the display exists */
return;
}
}

Variable Documentation

◆ tesaiot_display_ready

volatile uint8_t tesaiot_display_ready
extern

flag บอกสถานะการเปิดใช้งานแบบ 3 ค่า: 0 ยังไม่เสร็จ, 1 จอแสดงผลและ IPC พร้อม, 2 ขึ้นเฉพาะ IPC แบบ headless

ข้อกำหนดการเรียกใช้
ไม่มี header ที่ส่งมอบมาตัวใดประกาศตัวแปรนี้ (bento_secure_undeclared.h) ผู้ใช้ไลบรารีเป็นผู้เขียน extern volatile uint8_t ของตัวเอง และ volatile เป็นสิ่งที่ต้องมี — เพราะ GFX task เป็นฝ่ายเขียนค่าลงไป ให้วนถามค่านี้จาก FreeRTOS task หลัง scheduler เริ่มทำงานแล้วเท่านั้น โดยใช้ vTaskDelay — ห้ามวนรอแบบ busy spin และห้ามเรียกจาก main() การรอมีขอบเขตเสมอ (150 x 100 ms หรือ 10 000 ms) และเมื่อหมดเวลาให้ผ่านเลยไป ไม่ใช่ค้างรอต่อ มี 3 ค่า: 0 = ยังไม่เสร็จ, 1 = จอแสดงผลและ IPC พร้อม, 2 = ขึ้นเฉพาะ IPC แบบ headless ผู้เรียกทั้ง 2 รายที่มีอยู่จริงในของที่ส่งมอบตรวจด้วย == 0 การบูตแบบ headless จึงเดินต่อไปได้ วัตถุประสงค์ตามที่ผู้เรียกฝั่ง radar ระบุไว้: เลี่ยงการแย่งใช้บัสตอนเริ่มระบบกับการเปิดใช้งาน GFX / IPC
variant ที่ใช้ได้
mtb-mpy และ mtb-only
ตัวอย่าง — app task (เทมเพลต)
static void app_task(void *arg)
{
CY_UNUSED_PARAMETER(arg);
/* Wait for display + IPC initialization to complete
* tesaiot_display_ready: 0=pending, 1=display+IPC, 2=IPC-only (headless) */
extern volatile uint8_t tesaiot_display_ready;
uint32_t wait_count = 0;
while (tesaiot_display_ready == 0)
{
vTaskDelay(pdMS_TO_TICKS(100));
wait_count++;
if (wait_count > 150) {
break;
}
}
ตัวอย่าง — แบบที่กำหนดงบเวลาเป็นมิลลิวินาที (เทมเพลต, radar task)
void tesaiot_radar_task(void *arg)
{
(void)arg;
cy_rslt_t result;
/* Wait until display/IPC core is up to avoid startup bus contention with
* GFX/IPC bring-up on CM55. */
extern volatile uint8_t tesaiot_display_ready;
uint32_t wait_ms = 0U;
while ((tesaiot_display_ready == 0U) && (wait_ms < 10000U)) {
vTaskDelay(pdMS_TO_TICKS(50));
wait_ms += 50U;
}