Closed pq closed 5 years ago
Thanks for the test script. I’ll investigate!
On 8 Oct 2019, at 08:37, Phil Quitslund notifications@github.com wrote:
hacking up a monosynth patch and hit this while playing around w/ note retriggers.
here's a distilled test case that repros for me on norns w/ crow v1.0.0:
-- crow stress test
function init() end
local function sleep(n) os.execute("sleep " .. tonumber(n)) end
function redraw() print('stressing...') sleep(2) crow.send('^^v') for i=1,100 do print('>>') crow.output[2].volts = 0 crow.output[2].action = 'ar(1,5)' crow.output[2].execute() sleep(0.01) end print('done') end salient repl output:
... crow: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe') crow: no asl active /cc @trentgill @tehn
— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub, or mute the thread.
from user Dewb on lines. seems similar: Sure, happy to help! Here's a distilled example. I'm using crow 1.0.0 but I saw similar effects prior to the update. I'm using the USB cable that came with crow in the leftmost norns USB port.
[details="test script"]
-- crow: example of setting action on clock
local BeatClock = require 'beatclock'
local clk = BeatClock.new()
local function step()
local a = 4
local b = 2
local c = 5
crow.output[1].volts = a
crow.output[2].action = "pulse(0.1, 8, 0)"
crow.output[2].execute()
crow.output[3].volts = b
crow.output[4].volts = c
end
function init()
clk.on_step = step
clk.on_select_internal = function() clk:start() end
clk:add_clock_params()
params:set("bpm", 91)
params:default()
crow.reset()
clk:start()
end
function cleanup ()
clk:stop()
end
[/details]
This works initially -- but the pulse sounds too fast, almost double-time. And eventually, sometime between a couple triggers and a couple minutes later, it starts failing with this error:
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
crow receive: [string "local Asl = {}..."]:115: attempt to get length of a nil value (field 'exe')
Sometimes, if the script is able to run for a while, periodic instances of this error also appear in the console. Sometimes the error is accompanied by a single missed pulse, but not always.
crow receive: [string "eval"]:1: attempt to index a nil value (field 'vooutput')
If I move the crow.output[2].action
line into init()
after crow.reset()
, then I never see the local Asl
errors, and the timing on the pulse is correct. I do occasionally still see the attempt to index a nil value
message, but more rarely, sometimes with a dropped pulse also.
(In both cases, I also have about a 10% failure rate with hitting Play in maiden and having the script work, hitting Play again usually fixes it, maybe I need a delay after calling crow.reset()
?)
for exe
to be a nil value it likely means .action
is not receiving the arguments correctly. i'm guessing this is because of strings getting corrupted as they're sent norns -> crow.
the fact that it seems fine for some seconds to minutes before starting to fail suggests a memory issue. should try calling print(collectgarbage('count'))
before the .action
to see if failure is correlated to a higher RAM usage reading.
After some reflection I think the nil value (field 'vooutput')
error is a bigger issue than the repeated .action
assignment issue, as it results in dropped triggers with no workaround. Does it seem like the two symptoms are related, or should I file a separate issue?
The plot thickens. I did some more testing, and it looks like moving the crow.output[2].execute()
to the end of step()
, after the other outputs' .volts
are set is successful in preventing the nil value (field 'vooutput')
error. But I still got dropped triggers.
So I took a look at output 2 on an oscilloscope to see if the pulses were not being omitted, or if they were and Plaits was missing them. Surprisingly, the output was not a 0-8V pulse train, but a -5/+5 triangle LFO! (I'm guessing that's the default linear ramp LFO action behavior.) Changing the .action
set in init()
seemed to have no effect -- pulse
, ar
, whatever, I always got a triangle wave. (I think this explains the double-time triggers observed in my lines post.)
I moved the .action
back into step()
, and that made the oscilloscope output look as expected. I figured the .action
assignment immediately after reset()
is getting lost somehow, and indeed adding a metro delay of about 680ms in between calling crow.reset()
and crow.output[2].action = ...
seems to make the action take effect.
So it looks like there are three interesting things going on here:
crow.reset()
prevents scripts from communicating with crow for a period of time while it's removed/re-added. crow.output[n].volts = x
immediately after a crow.output[m].execute()
seems to interfere with the execution occasionally. (Filed this as https://github.com/monome/crow/issues/214)crow.output[n].action = f
too often results in errors (the original issue.)This seems like a race-condition between the slopes library & the usb-input, as it's norns specific. The same script running natively on crow doesn't have the problem.
Probably because either the .volts
or .execute
is creating a callback from C into Lua, right after the next command has been parsed & executed over USB.
I'm not entirely sure the best way to go about solving this. It seems the only reason to call .volts
and .action
in series is because you want to force the output to a predefined level before starting an envelope / lfo etc. Is the purpose pretty universally to set it to 0V before starting an envelope? If that's the desired behaviour, we can at least provide an additional argument to ar(attack-time, release-time, reset-to-zero)
to make the issue less present until we can solve it.
my use case was env re-trigger so something like reset-to-zero
would do it!
Fixed by #238
hacking up a monosynth patch and hit this while playing around w/ note retriggers.
here's a distilled test case that repros for me on norns w/ crow
v1.0.0
:salient repl output:
/cc @trentgill @tehn