On Fri, Sep 18, 2015 at 03:07:43PM +0100, Gavin Wraith wrote: > Has anyone any advice about the use of data synchronization > barriers when calling SWIs from C code compiled with GCC? > > To give RiscLua a command 'sys' analogous to BASIC's SYS > command I use this code > > asm volatile( > "stmfd sp!, {r4-r8,r12}" "\n\t" > "orr r12,%1,#0x20000 @ X-bit" "\n\t" > "mov r8,%2 @ register buffer" "\n\t" > "ldmia r8,{r0-r7}" "\n\t" > "swi 0x71 @ OS_CALLASWIR12" "\n\t" > "stmvcia r8,{r0-r7}" "\n\t" > "movvc r0,#0 @ 0 for success" "\n\t" > "ldmfd sp!,{r4-r8,r12}" "\n\t" > : "=r" (p): "r" (L),"r" (swinum), "r" (r) : "memory" ); > > entered with the SWI number in R1 and R2 pointing to a > buffer from which to load registers R0-R7 before entry, > and to which to save them on exit. I never thought much > about data synchronization, and when I compiled with > the Norcroft C compiler and Objasm it all worked fine > without. > Now I am using GCC and it does not seem to work.
In what way does it not seems to work? I'm not familiar with the asm side of GCC, but in general I would have expected that a DSB is not necessary here. DSB will ensure all in-flight memory accesses are completed before proceeding, and that any ongoing cache, branch predictor and TLB maintenance operations are completed. This is most relevant because the ARM memory model does not enforce ordering of memory operations except with explicit barriers - the instruction scheduler will identify load/store dependencies, but implicit dependencies (between cores, or via hardware eg address aliasing) have to be handled with barriers. The only relevant point here is that if you modify an instruction in memory, you need to achieve that there isn't a stale copy in the I-cache. That is acheived by an I-cache invalidate (of that line at least) and ISB. That's what OS_SynchroniseCodeAreas is for. In this case you're calling OS_CallASWI, so any synchronisation is a problem for it, not for you. If you were assembling SWI instructions manually then you would have to call OS_SynchroniseCodeAreas (or, less portably, do the invalidate yourself). https://en.wikipedia.org/wiki/Memory_ordering (which is worth a read) indicates that GCC >=4.4.0 supports __sync_sychronize to make it emit barriers. But that's almost certainly not required here. Theo _______________________________________________ GCCSDK mailing list gcc@gccsdk.riscos.info Bugzilla: http://www.riscos.info/bugzilla/index.cgi List Info: http://www.riscos.info/mailman/listinfo/gcc Main Page: http://www.riscos.info/index.php/GCCSDK