Open Goodfeat opened 5 years ago
Is the do parking required to get the error? What does "Do parking" mean for you? Do you wait here until heaters are hot or do you disturb when it is waiting for extruder temperature?
From description it sounds like you manage to leave the main look that polls commands and never come back so commands start piling up in host. But I need to see that myself I think to see what is happening.
parking is the g28 command
buffer = 3 Commands remain in the buffer after starting reprinting. It does not fix until you click on the reset
https://youtu.be/xFIcR6_K_xs this video is with a bug
Parking is called homing normally. I have tried it with latest 1.0.4 from thursday on a cartesian printer. Tested it 2 times with success. There I had fixed 2 things you mentioned in an earlier post (hopefully).
What does M119 return after homing for you? Should list all end stops as L or next homing will fail at least in newer firmware versions.
So I'm not sure if the bug is fixed or delta specific. If you do not home before starting your print would it then work as then endstops are not triggered?
After the commands remain in the buffer, no other command executes. Not M119, not even M112. The firmware goes into a “while” loop. But it does not freeze and continues to show data about temperatures. I tried using the standard configuration.h file with minimal changes. Corrected only limit switches and stepper motors. Surprisingly, out of 20 tests, it froze only once. Therefore, there is something in the configuration that prevents the normal operation of the printer. However, the problem comes out if you take another step - pulling the thread up by 100 mm.
This sequence of actions causes a stable freeze.
I found out that the host processes the stop as a pause, but this does not completely solve the problem. If you stop the printer via UI display, after the G28 and G1 E-100 command, the program freezes.
P.S noticed something: after G28, the extruder with the first command G1 E-100 does not want to execute the code
P.P.S You can reduce the order of the commands to 3, this takes you to the heart of the problem
P.P.P.S. Found the cause of the problem, but do not know yet what to do with it
the problem is Printer :: homeAxis lines in Printer.ccp 1580 updateCurrentPosition (true); 1588 Printer :: updateCurrentPosition ();
I commented on them and the problem went away. I keep testing like this, but surely there are some new bugs
I found what causes the error. The reason was not evident The code snippet because of which the bug occurs:
#define DISTORTION_CORRECTION 0 /// это вызывает ошибку при хоуминге при G28 и G1 E-100
#define DISTORTION_CORRECTION_POINTS 5
/** Max. distortion value to enter. Used to prevent dangerous errors with big values. */
#define DISTORTION_LIMIT_TO 2
/* For delta printers you simply define the measured radius around origin */
#define DISTORTION_CORRECTION_R 80
/* For all others you define the correction rectangle by setting the min/max coordinates.
Make sure the the probe can reach all points! */
#define DISTORTION_XMIN -110
#define DISTORTION_YMIN -110
#define DISTORTION_XMAX 110
#define DISTORTION_YMAX 110
If DISTORTION_CORRECTION 0, there are glitches with the buffer. If DISTORTION_CORRECTION 1, the bug disappears: at least now the printer is more stable. But why must I use this fuction if I do not need it?
I managed to solve the problem. It turns out under certain circumstances in fdifference [] the value is 0.00 or -0.00. This breaks the logic of the printer and stops it with an unloaded buffer.
This makes the value not equal to 0, but it still remains zero. Multiplication or division by zero creates an error.
The solution is simple: Since the root of the problem is somewhere in the depths of the firmware, I wrote a small check. It makes the correct value from float 0.00 to int 0
motion.cpp
void PrintLine::calculateDirectionAndDelta(float fdifference[], int32_t difference[],
ufast8_t *dir, int32_t delta[])
{
*dir = 0;
//Find direction
for(int i=0;i< 8;i++)
{
if(fdifference[i] > -0.001f && fdifference[i] <= 0 ||
fdifference[i] >= 0 && fdifference[i] < 0.001f )
{
fdifference[i]=0;
}
}
...
Buffer error does not occur
I'm sorry but that solution makes me not really happy. Apart from fdifference array only being 4 long the solution looks a bit arbitrary and will likely strike again for someone. I think the problem happens when the move contains 0 steps but gets added to the motion buffer. So error should be more in queueNonlinearMove. If I think the effect of your change cartesianDistance gets zero and cartesianDir is also 0 at least for these axis. I think problem only occurs if that happens to all directions. So it will run into
if (!(cartesianDir & XYZ_STEP))
{
queueEMove(difference[E_AXIS], check_endstops, pathOptimize);
return true;
}
which leads to no move if e has also no steps. So solution to not add a move with no steps is what is needed, but we should not use arbitrary testing values. If that only leads to one lost step your print is not perfect.
So lets look further. Without the mod we have a tiny motion, so seconds is a short time and segmentCount = RMath::max(1, static_cast<int16_t>(sps * seconds));
leads to one segment.
segmentCount = RMath::max(1, static_cast
```
if (virtualAxisSteps > p->delta[E_AXIS]) { // Is delta move or E axis leading p->stepsRemaining = virtualAxisSteps; axisDistanceMM[VIRTUAL_AXIS] = p->distance; //virtual_axis_move * Printer::invAxisStepsPerMM[Z_AXIS]; // Steps/unit same as all the towers // Virtual axis steps per segment p->numPrimaryStepPerSegment = maxStepsPerSegment;
if (cartesianDeltaSteps[Z_AXIS] > cartesianDeltaSteps[X_AXIS] && cartesianDeltaSteps[Z_AXIS] > cartesianDeltaSteps[Y_AXIS])
drivingAxis = Z_AXIS;
} else {
// Round up the E move to get something divisible by segment count which is greater than E move
p->numPrimaryStepPerSegment = (p->delta[E_AXIS] + segmentsPerLine - 1) / segmentsPerLine;
p->stepsRemaining = p->numPrimaryStepPerSegment * segmentsPerLine;
axisDistanceMM[VIRTUAL_AXIS] = -p->distance; //p->stepsRemaining * Printer::invAxisStepsPerMM[Z_AXIS];
drivingAxis = E_AXIS;
}
is the next code of importance. virtualAxisSteps will be 0 so we go to else part. You got problems at homing so delta[E_AXIS] = 0. numPrimaryStepPerSegment will be 0 leading to stepsRemaining = 0, but p->distance will be the small error distance we could not execute! drivingAxis is E_AXIS with 0 steps.
void PrintLine::calculateMove(float axisDistanceMM[], uint8_t pathOptimize, fast8_t drivingAxis) { if (stepsRemaining == 0) { // need at least one step for bresenham return; }
Is reponsible for pushing the line for execution, but with stepsRemaining = 0 it will not add it.
This is the analysis for 1.0.4. So as it looks it should not happen here. Not sure what version you are using. You seem to be using different version.
I'm currently repairing my delta, so hope I can test if I can produce the error. Will test with DISTORTION_CORRECTION = 0 also it is unclear why omitting a lot of code does cause precision problems. I also do not see where that tiny move comes from during homing where you get the block. All moves are normally more then 1 step. Maybe you can post your config here to see if there is something that is not expected by me.
Perhaps the solution is not perfect. I came to this solution because the fdifference [i] data is measured in millimeters. That is the form in which they appear in the host. I discovered that in g-code there really are extruder values that have 5 decimal places. To be precise. The whole thing is in the fdifference [Z_AXIS], it is not necessary to check the remaining axes and the extruder. There is an error in the Z axis. You could not check axes X,Y and E
I attach one working file and one test file which was configured on the site today. I needed it for verification. Both configurations cause an error
I also attached the modified motion.cpp file, where I made my changes.
I came to the conclusion that it makes no sense to reset the data you can simply add a check to the existing condition
if (fdifference[Z_AXIS] != 0 && difference[Z_AXIS] !=0 )// <----------------------------
{
if (fdifference[Z_AXIS] < 0)
{
delta[Z_AXIS] = -difference[Z_AXIS];
fdifference[Z_AXIS] = -fdifference[Z_AXIS];
*dir |= ZSTEP;
}
else
{
delta[Z_AXIS] = difference[Z_AXIS];
*dir |= Z_DIRPOS + ZSTEP;
}
}
else
{
delta[Z_AXIS] = 0;
}
It works and does not affect problems with small calculations. I looked at the debugger: the "difference" variable can be filled while the "fdifference" remains empty, but not vice versa
I think it will fit in as a temporary solution until you find a reason.
P.S. All the same, you need to add additional checks to all axes. After auto-calibration I caught a bug again
Unfortunately, my method does not work properly. After auto-calibration, problems with calculations begin. Everything gets worse if you change linear_advanced I set the value to 80, and now the extruder works completely inadequately
This happens even with the original motion.cpp. DISTORTION_CORRECTION 1 no longer corrects the situation.
I noticed that the value 1000 falls into the segmentCount
Should such a value fall into segmentCount?
Yes 1000 segments can happen if you have high value for segments per second. I have 600 so a 1.5 second move would already have 900 segments. What I noted is that your steps per mm values must be quite high. So I guess your CPU is working quite hard here. Not sure what you have for extrusion but 80 for advance is also a high value. My linear advance is normally 40-50 for direct extruder. For bowden it makes no sense as it would need to be so high that extrusion inverts direction all the time and can not follow.
I have to wait for a spare part for my delta to assemble it again:-( And it has only 80 steps per mm, so not sure if it reproduces the error at all.
but 1000 segments appeared during the team G1 E-100 ? I realized that when I squeeze the filament, the program should complete the next check.
if (!(cartesianDir & XYZ_STEP))
{
queueEMove(difference[E_AXIS], check_endstops, pathOptimize);
return true;
}
but the program is trying to make some kind of microscopic movement
queueEMove does not use subsegments at all if I see it correctly. So there should be no segments. So there must be a xyz move somehow that it does not go into the if cond. I assume the output will not be in queueEMove. So sure it happens with that move? Depending on what you did coordinates are taken from 2 different sources, but if you only have g0 moves around that should not be the reason.
I have to wait for a spare part for my delta to assemble it again:-( And it has only 80 steps per mm, so not sure if it reproduces the error at all.
I can try to reduce microstep until 80 and try to reproduce this error
I have two news, bad and good.
bad news: the problem with the bug has not gone away Good news: you can reproduce the error
I set microstep 1/16 = 80, the error did not disappear
I discovered the following. My printer has two extruders with different offsets. I made the printer autocalibrate. After that, I try to bring it home with the G28 team. The printer returns to the starting point. At this time, he is trying to establish the position according to the extruder offset (X-offset 7470), but without taking into account auto-calibration (fractionalSteps 147) ) The printer does not take calibration at G28 into account, although it must set the X-offset 7327 to currentPositionStep when completed. When I try to make the G1 E-100 command, instead of drawing in the plastic, the printer tries to set the offset according to auto calibration (7327). Therefore, the printer starts to fail, showing crazy segmentCount values (1000,1500,2500) In addition, with this error, the function PrintLine :: calculateDirectionAndDelta is called repeatedly (10-20 times in a row)
Why the G28 Team can not immediately set the correct offset of the extruder given the auto-calibration? How to make sure that the correct value is immediately written to Printer :: currentPositionSteps [i] by the command G28
My delta also has 2 extruders with offset in y direction. Looking into void Printer::homeZAxis() { // Delta z homing
you see near the end:
Extruder::selectExtruderById(Extruder::current->id);
Printer::zBabysteps = 0;
} here the selectExtruderById should have added the offset. Okay, as you say offset was added but the move was not executed which happened with the next E-100 move so it was not pure E move as I already thought. Now since E-100 takes a lot of time it generates lot of small segments as you already found out. I wonder if that is even causing the hang at the end (do you have this E-100 in your gcode you start?). Or is calling G28 several times in a row already enough to get the hang?
Hope I get my part early next week. They say 1-7 days delivery time. Then I can test. At least the removing of the offset is expected and happened as far as I remember, but that was x changes ago.
I make only two teams first G28 then G1 E100 I send all the codes from the host
I will continue to experiment
I discovered new bugs in the calculations. I am testing printer movement with console output with the values Printer :: currentPositionSteps [i] and fractionalSteps [i]. for (fast8_t i = 0; i <E_AXIS_ARRAY; i ++) { Printer :: currentPositionSteps [i] + = fractionalSteps [i]; Com :: printF (PSTR ("currentPosit ="), Printer :: currentPositionSteps [i]); Com :: printF (PSTR ("fractionalSteps ="), fractionalSteps [i]); } If you make G28, and then make the command to lower the extruder along the axis -Z10, then the data of Printer :: currentPositionSteps decreases (relative to the position of the auto-calibration). (7470> 7326> 7329> 7332 ...) Suppose this is correct, as the delta is slightly curved. The firmware allows for a slight tilt We switch the extruder from the first to the second, and then from the second to the first. Instead of returning to coordinate 7332, the extruder moves to coordinate 7479. Again, reduce the Z position down. Now Printer :: currentPositionSteps is starting to grow. (7479> 7482> 7485> 7488 ...) This is not normal!
Hi, I seem to have solved the hang problem. I added an extra move after turning on auto-level.
The code is as follows: printer.cpp
EVENT_BEFORE_Z_HOME;
homeZAxis ();
moveToReal (0, 0, Printer :: zLength - zBedOffset, IGNORE_COORDINATE, homingFeedrate [Z_AXIS]); // Move to designed coordinates including translation
updateCurrentPosition (true);
updateHomedAll ();
UI_CLEAR_STATUS
EVENT_AFTER_Z_HOME;
Commands :: printCurrentPosition ();
setAutolevelActive (autoLevel);
// --- now sets home with offets + autolevel
moveToReal (0, 0, Printer :: zLength - zBedOffset, IGNORE_COORDINATE, homingFeedrate [Z_AXIS]); // Move to designed coordinates including translation
updateCurrentPosition (true);
updateHomedAll ();
UI_CLEAR_STATUS
EVENT_AFTER_Z_HOME;
Commands :: printCurrentPosition ();
// --- end sets home with offets + autolevel
#if defined (SUPPORT_LASER) && SUPPORT_LASER
LaserDriver :: laserOn = oldLaser;
#endif
Printer :: updateCurrentPosition ();
setNoDestinationCheck (nocheck);
}
The printer needs the position to be correctly shifted not only with offset, but also with auto level, otherwise it causes bugs
While there were no failures, I also tested it with DISTORTION_CORRECTION 0 turned off, auto level turned off, auto level turned on with preliminary auto-calibration
True with one caveat I used mod in motion.cpp
if (fdifference [X_AXIS]! = 0 && difference [X_AXIS]! = 0)
if (fdifference [Y_AXIS]! = 0 && difference [Y_AXIS]! = 0)
if (fdifference [Z_AXIS]! = 0 && difference [Z_AXIS]! = 0)
if (fdifference [E_AXIS]! = 0 && difference [E_AXIS]! = 0)
Alas, but without it, hangs occur due to 0.00 in the fdifference. Unfortunately, I could not fix it
I found another bug. The error is related to the retract and the factor K and L The standard retract function does not work when you manually switch extruders. But I needed to roll back the plastic when switching the extruder I concluded that the G10 / G11 command should be placed in the lines:
and
but it does not work properly
EXT0_SELECT_COMMANDS when K is turned on, it starts to conflict with the K-factor
For example, with the K-factor of 10 turned on, after switching the extruder, the engine starts making strange sounds.
The most annoying thing is that because of the included K in the firmware, a failure occurs and the engine of the extruder may freeze and stop feeding plastic during printing. The same with the L-coefficient. He also trashes on my delta.
I tried not to use G10 / G11 commands, but to use a bunch from other commands.
However, the problem repeated again.
Hello, I found another bug because of which you cannot start printing again The reason of this bug is not clear, but it appears in several versions 1.04 It is possible to experience the bug even after reloading the arduino. The sequence of actions in which it appears:
This is only one procedure in which the bug is consistently experienced. In most cases, it gets out spontaneously: after canceling the print, or after calibrating the table. Less often it appears after manipulating with the settings of parking and switching on the heating elements the error can also appear when typing via octoprint or Cura, In addition, there is another error in which the printing works, but the plastic does not extrude, although the plastic extrusion counter works. Double reboot can fix it, but single reboot does not help These errors may be related to each other.
Arduino due + Ruramps4d, Delta printer