Too much output in Mk1 leads to insufficient memory?

Just a question to understand memory management on an E1 a bit better.

I’m using a parameterOnChange function, to send out SysEx when a change originates from the E1 itself. At the same time I was sending outputs for debugging reasons (see the print command) per change.
But I was getting "not enough memory " issues, so I added filters in the code not to show the results on incoming changes (origin = 1) and some other reasons. That explains why the screenshot texts are not consistent with the more recent code below.

I haven’t had memory issues yet since.

Question therefor is: can it be that when requesting too much output, this might cause some buffer in the E1 to fill in with queues (yet to print), resulting in an ‘out of memory’ state?

function parameterMap.onChange (valueObjects, origin, value)-- callback function retrieving MIDI value
  if origin == 1 then return end -- only process parameter Change when set from within the E1
  local parameterNumber = 0 
  local parameterType = 0
  local byte7 = 0
  for i, valueObject in ipairs (valueObjects) do
    local control  = valueObject:getControl ()
    parameterNumber = valueObject:getMessage():getParameterNumber ()
    parameterType   = valueObject:getMessage():getType ()
    if parameterNumber>=7000 then return end -- only send sysEx when parameter below 7000
    if parameterType~= 0 then return end-- only process virtual K4R parameters
    print(string.format ("Parameter %d (origin %d) => Control '%s'.%s with midiValue %d"
       , parameterNumber, origin, control:getName(), valueObject:getId(),value))
    --print(string.format ("   Control has minimum value %d and maximum value %d"
    --   , control:getValue("min"):getMin(), control:getValue("max"):getMax() ))
    break
  end

  if parameterNumber%1000 == 36 then byte7 = math.floor(value/128) end -- wave selection uses byte 7 to host bit 8 of the value
  midi.sendSysex (devPort, {0x40, channel-1, 0x10, 0x00, 0x04, parameterNumber%1000, math.floor(parameterNumber/1000)+byte7, value%128})
end

each Lua string concatenation results in allocation of a new chunk of memory. So it can eat emory quite quickly. E1 will performs garbage collection on regular basis, but if there is too much done in one function, it will not get to that point.

you might want to experiment with calling collectgarbage("collect") to control the process by yourself in the function.

There is an important thing to mention, the debugging messages are really meant for debugging and printing important messages. The log messages are actually sysex messages sent to the USB port. When logging is really verbose, it will generate huge amount of MIDI traffic.

1 Like

I got you. So there are two reasons to limit the use of the ‘print’ command:

  • reduce memory utilisation (especially on the Mk1. That’s why I currently keep developing on the Mk1. If it’ll work on the Mk1 , it should work on the Mk2 , but not the other way around)
  • reduce MIDI traffic.

One other thing. As I want to make a generic modulation matix piece of code, we then can reuse in severaly presets. One way might be to maintain 2 or 3 different 1-dimensional tables, but another solution would be the creation of a two dimensional array, filled with empty tables. Having 5 modulation sources, with two slots per source and 30 destinations would deliver an array with 300 empty tables. All in all only 10 tables would have values at any time. Is the impact of those 290-300 empty tables of any significance on the memory of an Mk1? If it is, I’ll concentrate on a solution with 3 one-dimensional arrays.

At this point, I’ll be adding some garbage collector functions to Minitaur and Notes transmittor, to see where memory usage is rising unnecessarily and then enforce a garbage collection cycle.