Home
JAQForum Ver 24.01
Log In or Join  
Active Topics
Local Time 00:05 22 Jun 2026 Privacy Policy
Jump to

Notice. New forum software under development. It's going to miss a few functions and look a bit ugly for a while, but I'm working on it full time now as the old forum was too unstable. Couple days, all good. If you notice any issues, please contact me.

Forum Index : Microcontroller and PC projects : CSubs: A new (easier) approach

Author Message
matherp
Guru

Joined: 11/12/2012
Location: United Kingdom
Posts: 11516
Posted: 06:26pm 20 Jun 2026
Copy link to clipboard 
Print this post

armcfgen.pdf

armcfgen.zip

We now have a python script that will compile, link and convert the C source for a CSUB to the basic statements required to run it. Full details of the new approach and how to use it are given in the manual. This is essentially a conversion of armcfgenV144.bas with a number of bugs fixed and a number of enhancements.
Specifically, the new version also includes everything needed to allow CSUBs to access constant data defined in the C source - there is an example in the manual
AND
CSUBs produced in this way and run on PicoMite versions 6.03.00RC22 and above will run on both RP2040 and RP2350 without any changes
The zip file contains the python program and the updated header PicoCFunctions.h needed to access the internal firmware functions. These are all described in the manual.

An example of the command to create a CSUB would be:
python armcfgen.py merge.c --compile -n times3 -e scale3 -O s -I d:\Dropbox\PicoMite\PicoMite

This says convert the file merge.c which will need compiling. Name the CSUB times3 and use as the entry point the function scale3, optimise it for size, and find the header file in the directory "d:\Dropbox\PicoMite\PicoMite"

For reference below is the csub that works the magic in the bubble universe demo
/* bubble.c - "bubble universe" inner loop as a PicoMite CSUB.
*
* One frame row (66 points): the sin/cos recurrence + scale + offset, producing
* integer screen coordinates in c() and d(). Moving this out of the BASIC
* interpreter took the demo from 233 ms/frame to ~23 ms.
*
* Build (compute-heavy -> ask for -Os; -I points at PicoCFunctions.h):
*     python armcfgen.py bubble.c --compile -n bubblerow -e bubblerow -O s -I <firmware dir>
*
* Call from BASIC:
*     CSUB bubblerow INTEGER, INTEGER, FLOAT      ' c(), d(), pf()
*     ...
*     pf(0)=i : pf(1)=r*i+t
*     bubblerow c(), d(), pf()
*
* pf(): 0=iang(i)  1=b(r*i+t)  2=v(state)  3=x(state)  4=pi/2
*       5=xs  6=ys  7=xc  8=yc      (v,x persist in pf(2)/pf(3) across calls)
*
* Uses PicoCFunctions.h: all double maths goes through the firmware CallTable
* (Sine/FAdd/FMul/FloatToInt), which the header locates at runtime via VTOR - so
* no CallTable argument and no chip-/build-specific address, one blob for every
* variant and both chips. (The per-call base re-read the wrappers do is lost in
* the noise here - the software Sine calls dominate.)
*/
#include "PicoCFunctions.h"

long long bubblerow(long long *c, long long *d, double *pf)
{
   double iang = pf[0], b = pf[1], v = pf[2], x = pf[3], hp = pf[4];
   double xs = pf[5], ys = pf[6], xc = pf[7], yc = pf[8];
   int j;

   for (j = 0; j < 66; j++) {
       double A   = FAdd(iang, v);
       double siv = Sine(A);
       double civ = Sine(FAdd(A, hp));     /* cos(i+v) = sin(i+v + pi/2) */
       double sx  = Sine(x);
       double cx  = Sine(FAdd(x, hp));     /* cos(x) */
       double uu  = FAdd(siv, sx);
       v = FAdd(civ, cx);
       x = FAdd(uu, b);
       c[j] = FloatToInt(FAdd(FMul(uu, xs), xc));
       d[j] = FloatToInt(FAdd(FMul(v,  ys), yc));
   }
   pf[2] = v;
   pf[3] = x;
   return 0;
}

Edited 2026-06-21 04:41 by matherp
 
Print this page


To reply to this topic, you need to log in.

The Back Shed's forum code is written, and hosted, in Australia.
© JAQ Software 2026