• R/O
  • SSH
  • HTTPS

chibios: Commit


Commit MetaInfo

Revisión15631 (tree)
Tiempo2022-05-19 22:28:53
Autorgdisirio

Log Message

Implemented VRQ-wait pseudo instuctions, fixed some more problems in VRQ handling.

Cambiar Resumen

Diferencia incremental

--- trunk/os/sb/common/sbsysc.h (revision 15630)
+++ trunk/os/sb/common/sbsysc.h (revision 15631)
@@ -49,6 +49,7 @@
4949 #define SB_SYSC_EVENT_WAIT_ALL 10
5050 #define SB_SYSC_EVENT_BROADCAST 11
5151 #define SB_SYSC_LOADELF 12
52+#define SB_SYSC_VRQ_WAIT 247
5253 #define SB_SYSC_VRQ_SETWT 248
5354 #define SB_SYSC_VRQ_CLRWT 249
5455 #define SB_SYSC_VRQ_SETEN 250
--- trunk/os/sb/host/sb.h (revision 15630)
+++ trunk/os/sb/host/sb.h (revision 15631)
@@ -280,6 +280,10 @@
280280 * @brief Mask of pending virtual IRQ flags.
281281 */
282282 sb_vrqmask_t vrq_wtmask;
283+ /**
284+ * @brief Reference to sh SB thread while waiting for VRQs.
285+ */
286+ thread_reference_t vrq_trp;
283287 #endif
284288 #if (SB_CFG_ENABLE_VFS == TRUE) || defined(__DOXYGEN__)
285289 /**
--- trunk/os/sb/host/sbapi.c (revision 15630)
+++ trunk/os/sb/host/sbapi.c (revision 15631)
@@ -76,6 +76,7 @@
7676 * @{
7777 */
7878 #if (SB_CFG_ENABLE_VRQ == TRUE) || defined(__DOXYGEN__)
79+#define SB_SVC247_HANDLER sb_api_vrq_wait
7980 #define SB_SVC248_HANDLER sb_api_vrq_setwt
8081 #define SB_SVC249_HANDLER sb_api_vrq_clrwt
8182 #define SB_SVC250_HANDLER sb_api_vrq_seten
@@ -1219,8 +1220,6 @@
12191220
12201221 void __sb_abort(msg_t msg) {
12211222
1222- chSysUnlock();
1223-
12241223 sb_cleanup();
12251224
12261225 chSysLock();
--- trunk/os/sb/host/sbvrq.c (revision 15630)
+++ trunk/os/sb/host/sbvrq.c (revision 15631)
@@ -52,7 +52,7 @@
5252 __STATIC_FORCEINLINE void vrq_makectx(sb_class_t *sbp,
5353 struct port_extctx *newctxp,
5454 uint32_t active_mask) {
55- uint32_t irqn = 31U - __CLZ(active_mask);
55+ uint32_t irqn = __CLZ(__RBIT(active_mask));
5656 sbp->vrq_wtmask &= ~(1U << irqn);
5757
5858 /* Disabling VRQs globally during processing.*/
@@ -67,7 +67,7 @@
6767 #endif
6868 }
6969
70-static void vrq_check_trigger(sb_class_t *sbp, struct port_extctx *ectxp) {
70+static void vrq_check_trigger_s(sb_class_t *sbp, struct port_extctx *ectxp) {
7171
7272 /* Triggering the VRQ if required.*/
7373 if ((sbp->vrq_isr & SB_VRQ_ISR_DISABLED) == 0U) {
@@ -81,6 +81,7 @@
8181 if (!sb_is_valid_write_range(sbp,
8282 (void *)ectxp,
8383 sizeof (struct port_extctx))) {
84+ chSysUnlock();
8485 __sb_abort(CH_RET_EFAULT);
8586 }
8687
@@ -116,6 +117,8 @@
116117
117118 chDbgCheckClassS();
118119
120+ chDbgAssert(sbp->tp->state != CH_STATE_CURRENT, "current");
121+
119122 /* Adding VRQ mask to the pending mask.*/
120123 sbp->vrq_wtmask |= vmask;
121124
@@ -142,6 +145,8 @@
142145 /* Building the return context.*/
143146 vrq_makectx(sbp, newctxp, active_mask);
144147 __port_syscall_set_u_psp(sbp->tp, newctxp);
148+
149+ chThdResumeS(&sbp->vrq_trp, MSG_OK);
145150 }
146151 }
147152 }
@@ -172,9 +177,20 @@
172177
173178 /* This IRQ could have preempted the sandbox itself or some other thread,
174179 handling is different.*/
175- if (sbp->tp->state == CH_STATE_CURRENT) {
180+ if ((sbp->tp->state == CH_STATE_CURRENT)) {
176181 /* Sandbox case, getting the current exception frame.*/
177- ectxp = (struct port_extctx *)__get_PSP();
182+ if ((__get_CONTROL() & 1U) == 0U) {
183+ /* If preempted in privileged mode then getting the store U_PSP
184+ value.*/
185+ ectxp = (struct port_extctx *)sbp->tp->ctx.syscall.u_psp;
186+ }
187+ else {
188+ /* If preempted in unprivileged mode then getting the current PSP
189+ value, it is U_PSP.*/
190+ ectxp = (struct port_extctx *)__get_PSP();
191+ }
192+
193+ /* Creating new context for the VRQ.*/
178194 newctxp = ectxp - 1;
179195
180196 /* Checking if the new frame is within the sandbox else failure.*/
@@ -212,20 +228,42 @@
212228 }
213229 }
214230
231+ chThdResumeI(&sbp->vrq_trp, MSG_OK);
232+
215233 chSysUnlockFromISR();
216234
217235 return;
218236 }
219237
238+void sb_api_vrq_wait(struct port_extctx *ectxp) {
239+ sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
240+ sb_vrqmask_t active_mask;
241+
242+ (void)ectxp;
243+
244+ chSysLock();
245+
246+ active_mask = sbp->vrq_wtmask & sbp->vrq_enmask;
247+ if (active_mask != 0U) {
248+ chThdSuspendS(&sbp->vrq_trp);
249+ }
250+
251+ chSysUnlock();
252+}
253+
220254 void sb_api_vrq_setwt(struct port_extctx *ectxp) {
221255 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
222256 uint32_t m;
223257
258+ chSysLock();
259+
224260 m = ectxp->r0;
225261 ectxp->r0 = sbp->vrq_wtmask;
226262 sbp->vrq_wtmask |= m;
227263
228- vrq_check_trigger(sbp, ectxp);
264+ vrq_check_trigger_s(sbp, ectxp);
265+
266+ chSysUnlock();
229267 }
230268
231269 void sb_api_vrq_clrwt(struct port_extctx *ectxp) {
@@ -232,9 +270,13 @@
232270 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
233271 uint32_t m;
234272
273+ chSysLock();
274+
235275 m = ectxp->r0;
236276 ectxp->r0 = sbp->vrq_wtmask;
237277 sbp->vrq_wtmask &= ~m;
278+
279+ chSysUnlock();
238280 }
239281
240282 void sb_api_vrq_seten(struct port_extctx *ectxp) {
@@ -241,11 +283,15 @@
241283 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
242284 uint32_t m;
243285
286+ chSysLock();
287+
244288 m = ectxp->r0;
245289 ectxp->r0 = sbp->vrq_enmask;
246290 sbp->vrq_enmask |= m;
247291
248- vrq_check_trigger(sbp, ectxp);
292+ vrq_check_trigger_s(sbp, ectxp);
293+
294+ chSysUnlock();
249295 }
250296
251297 void sb_api_vrq_clren(struct port_extctx *ectxp) {
@@ -252,25 +298,37 @@
252298 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
253299 uint32_t m;
254300
301+ chSysLock();
302+
255303 m = ectxp->r0;
256304 ectxp->r0 = sbp->vrq_enmask;
257305 sbp->vrq_enmask &= ~m;
306+
307+ chSysUnlock();
258308 }
259309
260310 void sb_api_vrq_disable(struct port_extctx *ectxp) {
261311 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
262312
313+ chSysLock();
314+
263315 ectxp->r0 = sbp->vrq_isr;
264316 sbp->vrq_isr |= SB_VRQ_ISR_DISABLED;
317+
318+ chSysUnlock();
265319 }
266320
267321 void sb_api_vrq_enable(struct port_extctx *ectxp) {
268322 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
269323
324+ chSysLock();
325+
270326 ectxp->r0 = sbp->vrq_isr;
271327 sbp->vrq_isr &= ~SB_VRQ_ISR_DISABLED;
272328
273- vrq_check_trigger(sbp, ectxp);
329+ vrq_check_trigger_s(sbp, ectxp);
330+
331+ chSysUnlock();
274332 }
275333
276334 void sb_api_vrq_getisr(struct port_extctx *ectxp) {
@@ -283,6 +341,8 @@
283341 sb_class_t *sbp = (sb_class_t *)chThdGetSelfX()->ctx.syscall.p;
284342 sb_vrqmask_t active_mask;
285343
344+ chSysLock();
345+
286346 /* VRQs must be disabled on return, sanity check.*/
287347 if (((sbp->vrq_isr & SB_VRQ_ISR_DISABLED) == 0U)) {
288348 __sb_abort(CH_RET_EFAULT);
@@ -303,6 +363,8 @@
303363 }
304364
305365 __port_syscall_set_u_psp(sbp->tp, ectxp);
366+
367+ chSysUnlock();
306368 }
307369
308370 #endif /* SB_CFG_ENABLE_VRQ == TRUE */
--- trunk/os/sb/host/sbvrq.h (revision 15630)
+++ trunk/os/sb/host/sbvrq.h (revision 15631)
@@ -66,6 +66,7 @@
6666 #endif
6767 void sbVRQTriggerS(sb_class_t *sbp, sb_vrqmask_t vmask);
6868 void sbVRQTriggerFromISR(sb_class_t *sbp, sb_vrqmask_t vmask);
69+ void sb_api_vrq_wait(struct port_extctx *ectxp);
6970 void sb_api_vrq_setwt(struct port_extctx *ectxp);
7071 void sb_api_vrq_clrwt(struct port_extctx *ectxp);
7172 void sb_api_vrq_seten(struct port_extctx *ectxp);
--- trunk/os/sb/user/sbuser.h (revision 15630)
+++ trunk/os/sb/user/sbuser.h (revision 15631)
@@ -844,6 +844,16 @@
844844 }
845845
846846 /**
847+ * @brief VRQ @p wait pseudo-instruction.
848+ *
849+ * @api
850+ */
851+static inline void __sb_vrq_setwt(void) {
852+
853+ __syscall0(247);
854+}
855+
856+/**
847857 * @brief VRQ @p setwt pseudo-instruction.
848858 *
849859 * @param[in] m VRQs mask
Show on old repository browser