ブートの処理 #2 ▪ 標準にないCSRの設定などをやる。 ▪ Nuclei社の拡張CSRのMMISC_CTLを設定 (0x200=NMIハンドラのアドレスにmtvecの値を共 有する) ▪ mtvecに割り込みハンドラを設定 ▪ mtvecの下位2ビットを3に設定して、Nuclei社の ECLIC割り込みコントローラを使う設定を行う。(ISA では0, 1しか定義していない。) ▪ mcountinhibitを無効にする。(電力消費を抑える) ▪ 最後に__resetに飛ぶ。(__resetはそのまま __initialize)を呼ぶ。 /* Set the the NMI base to share with mtvec by setting CSR_MMISC_CTL */ li t0, 0x200 csrs CSR_MMISC_CTL, t0 /* Initial the CSR MTVEC for the Trap ane NMI base addr */ la t0, trap_entry csrw mtvec, t0 /* Direct Mode: All exceptions set pc to BASE. */ csrc mtvec, 0x3 /* Disable performance counter */ csrsi mcountinhibit, 0x5 /* Jump to __reset */ tail __reset soc/riscv/riscv-privilege/gd32vf103/entry.S
影響箇所 ▪ SOC_MCAUSE_EXP_MASKの値を configurableにした ▪ 割り込みハンドラの__irq_wrapperの中 で、mcauseの値を見て、処理の分岐を 行っている。 ▪ ECALL割り込みが正しく処理できなかった ので、コンテキストスイッチができなかった。 /* Get IRQ causing interrupt */ csrr a0, mcause li t0, SOC_MCAUSE_EXP_MASK and a0, a0, t0 /* * Clear pending IRQ generating the interrupt at SOC level * Pass IRQ number to __soc_handle_irq via register a0 */ jal ra, __soc_handle_irq /* * If the exception is the result of an ECALL, check whether to * perform a context-switch or an IRQ offload. Otherwise call _Fault * to report the exception. */ csrr t0, mcause li t2, SOC_MCAUSE_EXP_MASK and t0, t0, t2 /* * If mcause == SOC_MCAUSE_ECALL_EXP, handle system call from * kernel thread. */ li t1, SOC_MCAUSE_ECALL_EXP beq t0, t1, is_kernel_syscall arch/riscv/core/isr.S
クローンチップであることによる足枷 ▪ クローン元のドライバには相乗りできない。 ▪ クローン元の会社さんも開発リソースを投入してZephyrにContributeしている。 ▪ ほぼ同じソースで動くのはわかっているが、仁義としてダメ。 ▪ 実際、RISC-VのIPコアを開発しているNuclei社の開発者はこの移植のdiscussionに 参加しているが、SoCベンダさんの開発者は一切タッチしていない。 ▪ 故に、部外者の私が移植を行う余地があったとも言える。 ▪ GD32にアンタッチャブル感があったので、ひょっとしたら派手に横紙破りをやった格好? ▪ したがって、GD32Vの開発は「コミュニティドリブン」で進んでいる、という建て付け。 ▪ アクティブな開発者が新しい実装を試す実験場にしてる?! Please, do not mention STM32 at Zephyr. Everybody knows that there are GigaDevices that can replace STM32. というアドバイスをメールで頂戴した。