ข้ามไปยังเนื้อหา

ลงทะเบียนด้วย CSR

วิดีโอประกอบ

ดูบน YouTube (เปิดในแท็บใหม่)

วิดีโอโดย สมาคมสมองกลฝังตัวไทย (TESA) · ดูทั้งชุดใน playlist AIoT Foundation

โมดูล 5 · การลงทะเบียนอุปกรณ์อย่างปลอดภัย · ภาพรวมโมดูล · หน้าหลักสูตร

อุปกรณ์ออกจากโรงงานพร้อมใบรับรองของ Infineon ซึ่งบอกได้แค่ว่าเป็น Trust M ของแท้ (บทเรียน 3.1) การลงทะเบียนคือการได้ใบรับรองที่ แพลตฟอร์มของเรา ออกให้ ผูกกับ device_id ของอุปกรณ์เครื่องนั้น โดยที่กุญแจลับไม่เคยออกจากชิปเลยสักครั้ง

เมื่อจบบทเรียนนี้ คุณจะ:

  1. อธิบายเนื้อหาของ CSR และเหตุผลที่กุญแจลับไม่ต้องออกจากชิป
  2. ติดตามคำขอด้วย correlation id และ OID ปลายทางตามตัวอย่างของ SDK
  3. ระบุสัญญาเรื่องบัฟเฟอร์ที่ฟังก์ชันส่ง CSR กำหนดให้ผู้เรียก
  • เรียนมาก่อน: บทเรียน 4.2: Protected Update และเรื่องใบรับรองใน บทเรียน 1.2
  • บนคอมพิวเตอร์: openssl และไฟล์ lab_key.pem ที่สร้างใหม่ได้ตามแล็บ 1.2 ข้อ 5
  • บนบอร์ด: แม่แบบของ SDK ที่ build ได้ แล็บเสริมที่ลงทะเบียนจริงต้องมีอุปกรณ์ที่เชื่อมต่อแพลตฟอร์มได้แล้ว (บทเรียน 3.2) และได้รับอนุญาตจากผู้สอน
  • อ่านคู่กัน: บทเรียน 5.3 ของ TESAIoT Firmware Stack: PSoC Edge E84 กับ OPTIGA™ Trust M

เมื่อกด HSM Security → Enrol Certificate บนจอ บท D2 ของเอกสาร SDK บอกว่าจอจะขึ้นเจ็ดประโยคนี้ตามลำดับ

Connecting to the platform
Generating a key pair inside the secure element
Signing the request with the key that never leaves the chip
Sending the request to the platform
Waiting for the platform
Checking the certificate against the key in the chip
The device can prove it holds the key this certificate names

ทายก่อน: ประโยคที่สามบอกว่ามีการ “ลงนามคำขอ” ถ้าคำขอมีกุญแจสาธารณะอยู่แล้ว ทำไมยังต้องลงนามอีก และใครเป็นคนตรวจลายเซ็นนั้น

1. CSR คืออะไร และทำไมกุญแจลับไม่ต้องออกจากชิป

หัวข้อที่มีชื่อว่า “1. CSR คืออะไร และทำไมกุญแจลับไม่ต้องออกจากชิป”

CSR (certificate signing request) ตาม RFC 2986 (PKCS #10) มีสามส่วนหลัก subject ชื่อที่ขอให้ใส่ในใบ กุญแจสาธารณะ ที่ขอให้รับรอง และ ลายเซ็น ที่ผู้ขอลงบนสองส่วนแรกด้วยกุญแจลับคู่กัน

คำตอบของคำทายอยู่ที่ลายเซ็นนี้ มันคือ proof of possession ผู้ออกใบตรวจลายเซ็นด้วยกุญแจสาธารณะในคำขอ ถ้าผ่าน แปลว่าผู้ขอถือกุญแจลับของคู่นั้นจริง ผู้ออกใบจึงไม่เคยต้องเห็นกุญแจลับเลย ใบที่ออกมาคือ subject กับกุญแจสาธารณะเดิม บวก issuer และช่วงเวลา แล้วลงนามโดย CA

บนบอร์ดของเรา บท D2 ระบุว่า subject เป็น CN=<mqtt username>,O=TESAIoT คู่กุญแจถูกสร้าง ในชิป แล้วคำขอถูกลงนามด้วยกุญแจที่ไม่ออกจากชิป ขั้นตอนเต็มตามคอมเมนต์หัวไฟล์ 05_csr_enrolment.c

  1. อุปกรณ์สร้างคู่กุญแจในชิป แล้วสร้าง CSR แบบ PEM จากกุญแจสาธารณะ (ส่วนนี้เป็นงานของ consumer ตามรายการ consumer_must_provide.txt)
  2. publish_csr() ห่อ CSR เป็น JSON แล้ว publish ไปที่ device/<id>/commands/csr บน session MQTT ที่เปิดอยู่
  3. แพลตฟอร์มลงนามและตอบกลับบนอีกหัวข้อหนึ่ง ตามสัญญา PU ของ SDK คือ commands/certificate โดยตรง ไม่มี manifest
  4. subscriber ของอุปกรณ์รับใบรับรองแล้วเขียนลงช่อง จากนั้นตรวจว่าใบเข้าคู่กับกุญแจในชิป (optiga_verify_cert_key_pair)

CSR_SUBMISSION_CONTRACT.md ของ SDK ให้กฎที่ “เคยทำให้ใครสักคนเสียเวลา debug มาแล้ว” ไว้ที่หัวเอกสาร

  • หัวข้อใช้ device_id (UUID) เสมอ ไม่ใช่ UID ของ Trust M UID เป็น client id ของ MQTT ถ้าใช้ในหัวข้อ broker จะปฏิเสธขณะที่การเชื่อมต่อยังค้าง ข้อความจึงดูเหมือนหายไปเฉย ๆ
  • subscribe device/<id>/commands/# ก่อน publish CSR คำตอบไม่ถูก retain คำตอบที่มาก่อน subscription สำเร็จหายไปเลย
  • ต้องมีคนดูแล session ไม่มี PINGREQ broker ปิด session ที่ 90 วินาที คำตอบที่มาทีหลังก็หาย
  • CSR ที่ถูกปฏิเสธเงียบ ไม่มีอะไรตอบกลับบนหัวข้อ เหตุผลอยู่ใน log ของแพลตฟอร์ม และ CSR ต้องยาวกว่า 100 ไบต์
  • มีอีกทางคือ HTTPS สำหรับผู้ดูแลหรือระบบหลังบ้านที่ถือ JWT แต่อุปกรณ์ที่ใช้ใบจากโรงงานอยู่ใช้ทาง MQTT

05_csr_enrolment.c อธิบายตัวอ่านสามตัว และ กับดักในสองตัว

  • trustm_current_correlation_id() คือ id ใหม่ที่ publish_csr() สร้างจาก TRNG ทุกครั้งที่เรียก คำตอบของแพลตฟอร์มถูกจับคู่กับ id นี้ NULL แปลว่าไม่มีอะไรค้างอยู่
  • trustm_requested_target_oid() และ trustm_requested_anchor_oid() คือคู่ OID ที่คำขอ Protected Update ครั้งล่าสุดระบุ publish_csr() ไม่ได้ตั้งค่าสองตัวนี้ มันถูกเขียนโดย tesaiot_publish_protected_update() เท่านั้น และอ่านได้ 0xE0E1 / 0xE0E8 หลังรีเซ็ต หลังเรียก publish_csr() อย่างเดียว สองค่านี้จึงบอกเรื่องของคำขอ PU ครั้งก่อนหรือค่าเริ่มต้น ไม่เคยบอกเรื่อง CSR นี้ อย่าใช้ติดป้ายการลงทะเบียนแบบ CSR อย่างเดียว

กติกาของการรีเซ็ต trustm_reset_state() ล้าง correlation id ถ้าเรียกตอนคำตอบยังไม่มา ใบรับรองที่มาถึงจะไม่มีอะไรให้จับคู่ และถูกทิ้งโดยไม่มีใครอ่าน ให้รีเซ็ตเมื่อเสร็จ หรือเมื่อหมดเวลาที่ คุณ ตัดสินใจเอง ไม่ใช่ “เพื่อความสะอาด” และถ้าจะรอผลด้วยตัวนับ ให้เก็บค่าตัวนับ ก่อน publish ตามกับดักข้อ 4 ของบท D2 ไม่อย่างนั้นงานที่จบก่อนหน้าจะถูกนับเป็นคำตอบของคำขอนี้

บท D2 เตือนอีกข้อ trustm_state_t เป็นแค่ตัวแปรที่มีเวลาประทับ ไม่ใช่ state machine ไม่มี switch ที่ขับเคลื่อนจากมัน และมีสี่ค่าที่ไม่มีใครเขียนในเส้นทางปกติ (APPLYING_UPDATE, WAITING_FOR_CERTIFICATE, COMPLETE, APPLYING_FRAGMENTS) หน้าจอที่รอ COMPLETE จะรอตลอดไป

ลายเซ็นของฟังก์ชันตาม เอกสาร tesaiot_hsm_api คือ

int publish_csr(uint8_t *csr, size_t csr_length, uint16_t target_oid, uint16_t trust_anchor_oid, uint32_t payload_version);

พารามิเตอร์แรกเป็น uint8_t * ไม่ใช่ const uint8_t * และตัวอย่าง 05 บอกว่านี่ไม่ใช่การพิมพ์ตก publish_csr() สร้าง JSON ทับลงในบัฟเฟอร์ของคุณ เพื่อไม่ต้องจองหน่วยความจำก้อนใหญ่ก้อนที่สอง ผลคือ

  1. บัฟเฟอร์ต้อง เขียนได้ สตริง PEM แบบ const ที่อยู่ใน flash ทำให้ fault
  2. บัฟเฟอร์ต้อง ใหญ่กว่า CSR ต้องจุ {"device_id":"<id>","csr":"<CSR ที่ escape \n แล้ว>","correlation_id":"<uuid>"} คือ CSR บวกหนึ่งไบต์ต่อการขึ้นบรรทัด บวกข้อความคงที่ราว 45 ไบต์ บวก device id และ correlation id ตัวอย่างแนะนำให้เผื่อ 256 ไบต์แล้วไม่ต้องคิดอีก
  3. csr_length คือ ความยาวของ CSR ไม่ใช่ขนาดบัฟเฟอร์
  4. CSR ของคุณหายไปเมื่อฟังก์ชันคืนค่า บัฟเฟอร์กลายเป็น JSON แล้ว ถ้าต้องใช้ CSR อีกให้เก็บสำเนาไว้ก่อน

trust_anchor_oid กับ payload_version ถูกรับไว้แต่ยังไม่ถูกใช้ (สงวนไว้) ตัวอย่างแนะนำให้ส่งค่าที่ตั้งใจจริงอยู่ดี เพื่อให้โค้ดยังถูกเมื่อวันหนึ่งมันเริ่มมีผล

ตัดจาก 05_csr_enrolment.c บรรทัด 158–172 และ 178–184 (TESAIoT PSE84 Dev Kit SDK, © Thai Embedded Systems Association, Apache-2.0)

/* Refuse rather than publish a fabricated CSR. A CSR the platform signs is
* a certificate on a real device; the wrong one is worse than none. */
if (s_csr_len == 0u) {
printf(" publish_csr() NOT called: s_csr is empty. Build a CSR first —\r\n"
" generate the keypair in the chip, then produce the PEM. The\r\n"
" archive cannot do this for you (optiga_generate_csr_pem is\r\n"
" in consumer_must_provide.txt).\r\n");
return SDK_EX_NO_DATA;
}
if (s_csr_len + 256u > sizeof(s_csr)) {
printf(" publish_csr() NOT called: %u-byte CSR in a %u-byte buffer "
"leaves no room for the JSON envelope built in place\r\n",
(unsigned)s_csr_len, (unsigned)sizeof(s_csr));
return SDK_EX_REFUSED;
}
int rc = publish_csr(s_csr, s_csr_len,
(uint16_t)EXAMPLE_TARGET_OID,
(uint16_t)EXAMPLE_ANCHOR_OID,
(uint32_t)EXAMPLE_PAYLOAD_VER);
/* s_csr now holds the JSON envelope, not the CSR. Do not reuse it as a CSR. */
s_csr_len = 0u;

สามจุดที่ควรลอกไปใช้

  1. ไม่ส่ง CSR ปลอม CSR ที่แพลตฟอร์มลงนามคือใบรับรองบนอุปกรณ์จริง ใบผิดแย่กว่าไม่มีใบ
  2. ตรวจที่ว่างก่อนเรียก ด้วยกฎ CSR + 256 ไบต์ ตัวอย่างใช้บัฟเฟอร์ static ขนาด 1280 ไบต์
  3. ทำให้ความยาวเป็นศูนย์ทันทีหลังเรียก เพื่อไม่ให้ใครเอาบัฟเฟอร์ที่เป็น JSON แล้วไปใช้เป็น CSR อีก

ตัวอย่างนี้ ปิดการ publish ไว้เป็นค่าเริ่มต้น ต้องมี session MQTT ที่เชื่อมต่อแพลตฟอร์มจริง และ CSR จริงที่สร้างจากกุญแจในชิป จึงจะเปิด DEFINES+=EXAMPLE_HSM_PUBLISH_CSR=1 คอมเมนต์บอกเหตุผลว่าคำขอที่ไม่มีทั้งสองอย่างเป็นแค่เสียงรบกวนบน broker ของคนอื่น

ใช้กฎของตัวอย่าง 05 ตัดสินแต่ละกรณีว่า เรียก publish_csr() ได้ หรือ ต้องแก้ก่อน และแก้อย่างไร

  1. static uint8_t buf[1280]; เก็บ CSR ยาว 620 ไบต์ แล้วเรียก publish_csr(buf, 620, 0xE0E1, 0xE0E8, 1) ____
  2. static const char csr[] = "-----BEGIN CERTIFICATE REQUEST-----\n..."; แล้วเรียก publish_csr((uint8_t *)csr, strlen(csr), ...) ____
  3. static uint8_t buf[700]; เก็บ CSR ยาว 620 ไบต์ ____
  4. publish_csr(buf, sizeof(buf), 0xE0E1, 0xE0E8, 1) โดย buf มี CSR ยาว 620 ไบต์ ____
  5. หลัง publish_csr() คืน 0 โปรแกรมพิมพ์ buf ออกมาเพื่อ “ดู CSR ที่ส่งไป” ____
  6. คำตอบยังไม่มา แต่โปรแกรมเรียก trustm_reset_state() เพื่อเริ่มสถานะใหม่ให้สะอาด ____
เฉลย
  1. เรียกได้ 620 + 256 = 876 ไม่เกิน 1280
  2. ต้องแก้ บัฟเฟอร์ const อยู่ใน flash เขียนไม่ได้ publish_csr() จะ fault ตอนสร้าง JSON ทับ ให้คัดลอกไปบัฟเฟอร์ที่เขียนได้ก่อน
  3. ต้องแก้ 620 + 256 = 876 เกิน 700 ไม่มีที่ให้ JSON ที่สร้างทับ
  4. ต้องแก้ csr_length ต้องเป็น 620 ไม่ใช่ขนาดบัฟเฟอร์
  5. ต้องแก้ ถึงตอนนั้น buf เป็น JSON ไปแล้ว ถ้าอยากเก็บ CSR ต้องคัดลอกไว้ก่อนเรียก
  6. ต้องแก้ การรีเซ็ตล้าง correlation id ใบรับรองที่มาถึงทีหลังจะถูกทิ้ง ให้รอจนเสร็จหรือจนหมดเวลาที่ตั้งใจไว้

คำถามข้างล่างเป็นส่วนหนึ่งของชุดเต็มใน quiz.yaml ซึ่งระบบตรวจอัตโนมัติใช้

  1. ทำไมแพลตฟอร์มออกใบรับรองให้ได้โดยไม่ต้องเห็นกุญแจลับของอุปกรณ์ (เป้าหมายข้อ 1)

    • ก) เพราะแพลตฟอร์มเดากุญแจลับจากกุญแจสาธารณะได้
    • ข) เพราะ CSR มีกุญแจสาธารณะ และลายเซ็นบน CSR พิสูจน์ว่าผู้ขอถือกุญแจลับคู่นั้น
    • ค) เพราะกุญแจลับถูกส่งไปแบบเข้ารหัส
    • ง) เพราะใบรับรองไม่เกี่ยวกับกุญแจ
    เฉลย

    ข นี่คือ proof of possession ใบที่ออกมาใส่กุญแจสาธารณะเดิม กุญแจลับจึงอยู่ในชิปต่อไป

  2. หลังเรียก publish_csr() อย่างเดียว trustm_requested_target_oid() บอกอะไร (เป้าหมายข้อ 2)

    • ก) ช่องที่ใบรับรองจาก CSR นี้จะถูกเขียน
    • ข) OID ของคำขอ Protected Update ครั้งก่อน หรือค่าเริ่มต้น 0xE0E1 ไม่ได้บอกเรื่อง CSR นี้
    • ค) UID ของชิป
    • ง) correlation id
    เฉลย

    ข ค่านี้ถูกเขียนโดย tesaiot_publish_protected_update() เท่านั้น ตัวติดตาม CSR คือ correlation id

  3. ข้อใดเป็นสัญญาเรื่องบัฟเฟอร์ของ publish_csr() (เป้าหมายข้อ 3)

    • ก) บัฟเฟอร์เป็น const ได้ และ csr_length คือขนาดบัฟเฟอร์
    • ข) บัฟเฟอร์ต้องเขียนได้ ใหญ่กว่า CSR พอให้ JSON ที่สร้างทับ csr_length คือความยาว CSR และ CSR หายไปหลังเรียก
    • ค) ฟังก์ชันจองบัฟเฟอร์ใหม่ให้เอง
    • ง) ต้องส่ง CSR แบบ DER เท่านั้น
    เฉลย

    ข ตัวอย่าง 05 เขียนไว้เป็นสี่ข้อ และแนะนำให้เผื่อ 256 ไบต์

แล็บหลัก: ติดตามคำขอโดยไม่ส่งจริง และอ่าน CSR ด้วยตา

  • build ตัวอย่าง 05 โดยไม่เปิดการ publish
    Terminal window
    make build ENABLE_PAGE_EXAMPLES=1 SDK_EXAMPLE_CM33=cm33/security/05_csr_enrolment
    make program BENTO_WORKSPACE="$(cd .. && pwd)"
    จดบรรทัด correlation id on entry, requested target OID, requested anchor OID, บรรทัดของ trustm_update_state และ trustm_reset_state แล้วข้อความ SKIPPED publish_csr() อธิบายว่าทำไมตัวอย่างกล้าเรียก trustm_reset_state() ตรงนั้น (ดูเงื่อนไขก่อนหน้า)
  • สร้าง CSR บนคอมพิวเตอร์จากกุญแจทดลองของบทเรียน 1.2 ใช้ UUID ปลอมที่เห็นชัดว่าปลอม แล้วอ่านทุกส่วน
    Terminal window
    openssl ecparam -name prime256v1 -genkey -noout -out lab_key.pem
    openssl req -new -key lab_key.pem -subj "/CN=00000000-0000-0000-0000-000000000000/O=TESAIoT" -out lab.csr
    openssl req -in lab.csr -noout -text
    openssl req -in lab.csr -noout -verify
    หา subject กุญแจสาธารณะ และอัลกอริทึมลายเซ็นในผลลัพธ์ บรรทัดสุดท้ายต้องบอกว่า self-signature verify OK นี่คือ proof of possession ที่ CA ตรวจ
  • นับขนาด wc -c < lab.csr และจำนวนบรรทัด grep -c '' lab.csr แล้วคำนวณว่าบัฟเฟอร์ของ publish_csr() ต้องใหญ่อย่างน้อยเท่าไรตามสูตรของตัวอย่าง 05 เทียบกับกฎ +256 ไบต์ แล้วลบไฟล์กุญแจทดลองทิ้ง
  • วาดแผนภาพลำดับของการลงทะเบียน แสดงหัวข้อ MQTT ทุกหัวข้อที่เกี่ยว (commands/#, commands/csr, commands/certificate) จุดที่ proof of possession ถูกตรวจ และจุดที่อุปกรณ์ตรวจว่าใบเข้าคู่กับกุญแจ

แล็บเสริม: ลงทะเบียนจริง ทำเมื่อผู้สอนอนุญาตเท่านั้น

การลงทะเบียนสร้างคู่กุญแจใหม่ในชิป กุญแจเดิมในช่องนั้นหายไปถาวร และเขียนใบรับรองใหม่ลงช่อง 0xE0E1 ด้วยการเขียนธรรมดา ถ้าช่องถูกล็อกโดย Protected Update ไว้ ปุ่มจะปฏิเสธก่อนทำอะไร

  • อุปกรณ์เชื่อมต่อแพลตฟอร์มได้ในโหมดที่ใช้อยู่ (บทเรียน 3.2) กด HSM Security → Enrol Certificate แล้วจดประโยคบนจอทั้งเจ็ดเทียบกับ “ดูของจริงก่อน”
  • จดบรรทัด [CSR] Using DIRECT PUBLISH ... และ [Subscriber] Certificate from platform (N bytes) บน UART ตามบท D2
  • เปลี่ยน tls_mode=mtls แล้วเชื่อมต่อใหม่ มองหาบรรทัด [mTLS] device pair verified — using TESAIoT identity ในบทเรียน 3.1 ซึ่งแปลว่าเฟิร์มแวร์เลือกใช้ใบและกุญแจที่คุณเพิ่งลงทะเบียน

การลงทะเบียนใช้เวลาหลายวินาทีและต้องรอแพลตฟอร์มได้ถึงหนึ่งนาที บทต่อไปดูว่าหน้าจอบนอุปกรณ์รับมือกับงานยาวแบบนี้อย่างไรโดยไม่ค้างและไม่เงียบ

บทเรียนถัดไป: บทเรียน 5.2: หน้าจอลงทะเบียนบนอุปกรณ์

  • ในระบบของคุณ มีที่ไหนที่ “ล้างสถานะให้สะอาด” แล้วทำให้คำตอบที่มาถึงทีหลังถูกทิ้ง
  • ถ้า CSR ที่ถูกปฏิเสธไม่มีอะไรตอบกลับเลย ทีมของคุณจะรู้ได้อย่างไร และจะดูหลักฐานจากไหน
  • ฟังก์ชันใน API ของคุณมีตัวไหนที่เขียนทับบัฟเฟอร์ของผู้เรียกโดยที่ชื่อหรือชนิดของพารามิเตอร์ไม่ได้บอก

คำถามทบทวน

ลองตอบเองก่อน แล้วค่อยเปิดดูเฉลย

  1. ทำไมแพลตฟอร์มออกใบรับรองให้ได้โดยไม่ต้องเห็นกุญแจลับของอุปกรณ์ (เป้าหมายข้อ 1)

    1. เพราะแพลตฟอร์มเดากุญแจลับจากกุญแจสาธารณะได้
    2. เพราะ CSR มีกุญแจสาธารณะ และลายเซ็นบน CSR พิสูจน์ว่าผู้ขอถือกุญแจลับคู่นั้น
    3. เพราะกุญแจลับถูกส่งไปแบบเข้ารหัส
    4. เพราะใบรับรองไม่เกี่ยวกับกุญแจ
    ดูเฉลย

    คำตอบ: B. เพราะ CSR มีกุญแจสาธารณะ และลายเซ็นบน CSR พิสูจน์ว่าผู้ขอถือกุญแจลับคู่นั้น

    นี่คือ proof of possession ตาม PKCS

  2. เลือกทุกข้อที่อยู่ใน CSR (เป้าหมายข้อ 1)

    1. subject ที่ขอให้ใส่ในใบ
    2. กุญแจสาธารณะ
    3. ลายเซ็นที่ลงด้วยกุญแจลับคู่กัน
    4. กุญแจลับ
    5. ลายเซ็นของ CA
    ดูเฉลย

    คำตอบ: A. subject ที่ขอให้ใส่ในใบ · B. กุญแจสาธารณะ · C. ลายเซ็นที่ลงด้วยกุญแจลับคู่กัน

    CSR ไม่มีกุญแจลับ และยังไม่มีลายเซ็นของ CA ลายเซ็นของ CA อยู่ในใบรับรองที่ออกมาภายหลัง

  3. หลังเรียก publish_csr() อย่างเดียว trustm_requested_target_oid() บอกอะไร (เป้าหมายข้อ 2)

    1. ช่องที่ใบรับรองจาก CSR นี้จะถูกเขียน
    2. OID ของคำขอ Protected Update ครั้งก่อน หรือค่าเริ่มต้น 0xE0E1 ไม่ได้บอกเรื่อง CSR นี้
    3. UID ของชิป
    4. correlation id
    ดูเฉลย

    คำตอบ: B. OID ของคำขอ Protected Update ครั้งก่อน หรือค่าเริ่มต้น 0xE0E1 ไม่ได้บอกเรื่อง CSR นี้

    ค่านี้ถูกเขียนโดย tesaiot_publish_protected_update() เท่านั้น ตัวติดตามคำขอ CSR คือ correlation id

  4. คำตอบของแพลตฟอร์มยังไม่มา แต่โปรแกรมเรียก trustm_reset_state() ผลคืออะไร (เป้าหมายข้อ 2)

    1. ไม่มีผล
    2. correlation id ถูกล้าง ใบรับรองที่มาถึงทีหลังไม่มีอะไรให้จับคู่และถูกทิ้ง
    3. ชิปสร้างกุญแจใหม่
    4. แพลตฟอร์มยกเลิกคำขอ
    ดูเฉลย

    คำตอบ: B. correlation id ถูกล้าง ใบรับรองที่มาถึงทีหลังไม่มีอะไรให้จับคู่และถูกทิ้ง

    ตัวอย่าง 05 ให้รีเซ็ตเมื่อเสร็จ หรือเมื่อหมดเวลาที่ตัดสินใจเอง ไม่ใช่เพื่อความสะอาด

  5. ข้อใดเป็นสัญญาเรื่องบัฟเฟอร์ของ publish_csr() (เป้าหมายข้อ 3)

    1. บัฟเฟอร์เป็น const ได้ และ csr_length คือขนาดบัฟเฟอร์
    2. บัฟเฟอร์ต้องเขียนได้ ใหญ่กว่า CSR พอให้ JSON ที่สร้างทับ csr_length คือความยาว CSR และ CSR หายไปหลังเรียก
    3. ฟังก์ชันจองบัฟเฟอร์ใหม่ให้เอง
    4. ต้องส่ง CSR แบบ DER เท่านั้น
    ดูเฉลย

    คำตอบ: B. บัฟเฟอร์ต้องเขียนได้ ใหญ่กว่า CSR พอให้ JSON ที่สร้างทับ csr_length คือความยาว CSR และ CSR หายไปหลังเรียก

    publish_csr() สร้าง JSON ทับในบัฟเฟอร์ของผู้เรียก ตัวอย่าง 05 แนะนำให้เผื่อ 256 ไบต์เหนือขนาด CSR

อ้างอิงบทเรียนนี้

ถ้านำบทเรียนนี้ไปสอน ทำสไลด์ หรือทำเอกสารต่อ ให้อ้างอิงด้วยข้อความนี้ ถ้าดัดแปลงเนื้อหา ให้เติม (ดัดแปลง)ต่อท้ายชื่อบทเรียน

"ลงทะเบียนด้วย CSR" จาก TESA Open Knowledge โดยสมาคมสมองกลฝังตัวไทย (Thai Embedded Systems Association: TESA) https://github.com/tesaiot/tesa-qualification-program สัญญาอนุญาต CC BY-NC 4.0

ข้อความอ้างอิงภาษาอังกฤษ: "Enrolment with a CSR" from TESA Open Knowledge by the Thai Embedded Systems Association (TESA), https://github.com/tesaiot/tesa-qualification-program, licensed under CC BY-NC 4.0

ลิงก์บทเรียน: https://tesaiot.github.io/tesa-qualification-program/courses/secure-iot-optiga/m05-provisioning/l01-csr-enrolment/

บทเรียนนี้ดัดแปลงจากต้นฉบับด้านล่าง เมื่ออ้างอิงให้คงเครดิตต้นฉบับไว้ด้วย
https://github.com/tesaiot/tesaiot-pse84-devkit-sdk/tree/ef72c1b658178eee8c38b1e47d28b006f80a59b5 · SDK security examples and docs are linked at this commit; lesson pages quote short excerpts with attribution and copy no files.

วิธีอ้างอิง TESA ฉบับเต็ม

TESA Open Knowledge · © 2026 สมาคมสมองกลฝังตัวไทย (TESA) · CC BY-NC 4.0

เนื้อหาเผยแพร่ภายใต้ CC BY-NC 4.0 นำไปใช้ต่อในงานที่ไม่ใช่เพื่อการค้าได้ โปรดอ้างอิงสมาคมสมองกลฝังตัวไทย (TESA) ทุกครั้ง · วิธีอ้างอิง TESA