-
• #2
Trying process.memory to attempt a debug
//xtest2.js 27 Jan2018 // trying this on a Pico //try changing the value of chk // process.memory uncommented =PM // comment out process.memory =NPM /// // chk=1*1024 works both cases // chk =2*1024 works with PM,fails NPM // chk=25*1024 works with PM, fails NPM // chk=26*1024 fails just too big var n =100, chk=25*1024; var tdata=new Uint8Array(chk); function xsend(a){ console.log(n,a.length); // process.memory();// this makes it work }//end xsend function test(){ var a; while (n){ xsend(E.toString(tdata)); //fails if no process.memory n--; } }//end test setTimeout(function () { test(); }, 1000);
The process.memory() fixes the bug.
1v95 Copyright 2017 G.Williams > =undefined 100 25600 99 25600 98 25600 97 25600 Uncaught Error: Field or method "length" does not already exist, and can't create it on undefined at line 16 col 16 console.log(n,a.length); ^ in function "xsend" called from line 23 col 26 xsend(E.toString(tdata)); //fails if no process.memory ^ in function "test" called from line 1 col 6 test(); ^ in function called from system >
-
• #3
You are creating a 23k string. That is quite large in espruino world!
The esp8266'has even less resources, so try changing the 23 to 4 and see if it works!
-
• #4
The example above is on a Pico.
It is an attempt to zero in on the bug first found in the following code.For the ESP8266 -01 try this code
//WSDesp8266A/js 27Jan2018 // using process.memory to fix bug //http//192.168.1.6:8080 //ESP8266 with Espruino flahed // list of Wifi and passwords var SSID="ssid"; var key="keykey"; var Startagain=0; var myinterval; var n =100, chk=2*1024; var tdata=new Uint8Array(chk); var i; for(i=0;i<1024;i++){ tdata[i]=0x30; tdata[i+1024]=0x31; }//next i var page = "<html>\r\n<body>\r\n<textarea id=\"demo\" rows=\"32\" cols=\"64\"></textarea>\r\n<script>\r\nvar ws;\r\nvar data=\"\";\r\n//setTimeout(function(){\r\nws = new WebSocket(\"ws://\" + location.host + \"/my_websocket\", \"protocolOne\");\r\nws.onmessage = function (event) { \r\ndata+=event.data;\r\ndocument.getElementById(\"demo\").innerHTML = data.length;\r\nws.send(\"Hello to Espruino!\"); \r\n };\r\n//setTimeout(function() { ws.send(\"Hello to Espruino!\"); }, //1000);}\r\n//,1000);\r\n\r\n</script></body>\r\n</html>\r\n" ; function onPageRequest(req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end(page); } function test(){ console.log("Start connection process"); var wifi = require("Wifi"); console.log("Try Connecting to WiFi ",SSID); wifi.connect(SSID,{password:key}, function(err) { console.log(err); if (err){Startagain=1;return; } console.log("connected? err=", err, "info=", wifi.getIP()); console.log("Wi-Fi Connected"); clearInterval( myinterval); var t=getTime(); var server = require('ws').createServer(onPageRequest); server.listen(8080); server.on("websocket", function(ws) { ws.on('message',function(msg) { n--; print("n=",n,"t:",(getTime()-t).toFixed(3),"sec"); print("[WS] "+JSON.stringify(msg)); if(n){ ws.send(E.toString(tdata)); process.memory(); } }); t=getTime(); ws.send(E.toString(tdata)); process.memory(); print("n=",n,"t:",(getTime()-t).toFixed(3),"sec"); }); });//end connect }//end test myinterval=setInterval(function () { console.log("Test for error"); if(Startagain){ Startagain=0; test(); }//end of Startagain }, 2000); test();
-
• #5
The issue you're hitting here is actually one of fragmentation. The standard Flat String allocator tries to allocate a flat string quickly - and if the free list (not the actual data!) gets fragmented it can fail.
I've now changed
E.toString
to try harder (which fixes your problem) but have also made is pass through Uint8Arrays if they're backed by a flat string - so in that case it'll make things much faster for you as well. -
• #6
Thanks!
Here is the test code
Here is the output
Similar problem on ESP8266 running Espruino, but different array sizes to get it to run at all.