Talk:G-code

From RepRap
Revision as of 16:24, 16 December 2013 by Free (talk | contribs) (Time for G-code V2)
Jump to: navigation, search

M104 & M109 Deprecation, G10 Introduction

No issues with deprecating M109, as this is an equivalent to M104 & M116. But M104? [heated bed (M140) example deleted]

I consider G10 head/tool offset a good idea, but temperatures should be set by it's own command. Also, one often sets a temperature only, keeping the geometrical offset.

If the L value is ignored, why is it part of the specification?

Last not least, Marlin people already defined M206 for the head offset. These two should be aligned.

--Traumflug 11:28, 19 July 2012 (UTC)

M140 seems unaffected, Traumflug, so you can set the bed temp without changes. That said, I don't like any of this one bit. I don't like that the fast temp setting is gone, and I don't like that mysterious temperatures come out of nowhere when switching tool. I'd much prefer G10 to deal with spatial offset only, and use M10{4|9} [T0] S200. It gives the gcode generator much more control over the process. Having an OPTIONAL temperature setting in G10 would be acceptable for me, but definitely not deprecating M104/M109

--Kliment

I don't quite see why temperature offsets are different from spatial offsets - it's just another dimension in which the machine operates. It seemed neater to me to set them all in one place. And temperatures don't come out of nowhere - they are values you have previously explicitly set...

Jean-Marc pointed out that it would be useful to have an option to save and load this stuff from eeprom like Marlin with M500 - that way you could have slightly different offsets for different machines and still run them all off the same G Code file.

I agree that M104 is useful as it allows you:

  1. to set temp and return
  2. to do stuff you know doesn't involve extruding
  3. to set same temp and wait

Which speeds things up a bit at the start of a print. I'm not quite sure what we should do about that.

As there is a standard (G10) for setting offset that pre-dates the invention of 3D printing, I think that's preferable to M206.

Finally - remember that the time interval between something being deprecated and something going away altogether can be arbitrarily long, and is entirely in the hands of people writing firmware :-)

- Adrian


I have no problem introducing a new command which is a superset of existing functionality, and even better if it is more standard compliant, but I can't see a good reason to remove the previous commands, as there is no conflict in functionality. Presumably if G10 returns an error, then the host must fall back to previous commands.

I don't know which standard you are looking at, but in mine (the official NIST standard) G10 does not set tool offsets. It appears some software out there is using a different, non-standard meaning for G10. I don't think non-standard use by one or more applications creates "a standard". Our use of G10 also has quite different parameters. This proposal would appear to be replacing non-standard command(s) with a new non-standard command, which doesn't help standardization and breaks compatibility.

--Bobc 21:41, 30 July 2012 (UTC)


Thanks for the comments so far. I see we agree on M109 being obsolete, so I've removed the discussion tag.

Regarding the NIST standard, G10 is described there as setting a coordinate system, so it's similar to setting a tool offset.

Not a word there on what L does, though. So I reduced it's description.

What's left is R and S, the standby and work temperatures. How about making them optional?

  • Without R and S, both default to zero, so we have the (former) behaviour without G10.
  • With R and/or S, temperatures are set at tool change time (T, M6 command).
  • M104 always sets the temperature of the current extruder. So it matches traditional behaviour in case R and S weren't used. In case R and/or S are used, M104 overrides the extruder's work temperature, but doesn't change the extruder's S setting.

--Traumflug 22:22, 31 July 2012 (UTC)


I don't see the same agreement on M109 that you do, unless you are ignoring specific objections.

I did a little digging, it appears the L parameter selects a "parameter number". So in NIST, L2 means "set coordinate system". FANUC systems use versions of G10 as "set tool offsets", sometimes L1, L10 or L12, sometimes omitted. Other L numbers may set other parameters, depending on machine. LinuxCNC appears to support several values of L. If we are using the parameters to mean something different (e.g R parameter is not used to define cutter radius), we should probably pick something like L3.

Ref LinuxCNC G Codes

--Bobc 08:02, 4 August 2012 (UTC)


Did I miss something? I see no vote for M109, just a combined one for M104/M109. How to replace M109 by M104 is described.

So, the L parameter is sort of a sub-command on a number of other, non RepRap G-code interpreters. Thanks a lot for the digging. Does that make the current description of the RepRap G-code flavour wrong? I think it's sufficient to describe what a RepRap firmware does, elaborating on what others do should go to something like a "G-code in General" wiki page.

--Traumflug 10:45, 4 August 2012 (UTC)

Has anyone implemented G10 in either a slicer or a firmware in the way described on the wiki? I am depending on M109s and M104s in prontserve to send the target temperature events but I can add G10 as well if this is actually used somewhere. Marlin seems to use it as a retract command (see https://github.com/ErikZalm/Marlin/blob/Marlin_v1/Marlin/Marlin_main.cpp#L771 ) and I guess I can just go off that.

TL;DR This is very unclear to me. This needs documentation.

--TheOtherRob 03:37, 27 June 2013 (UTC) (d1plo1d on github)

Checking

"These are the line number and the checksum. The RepRap firmware checks the checksum against a locally-computed value and, if they differ, requests a repeat transmission of the line of the given number. "

Surely the firmware must request resending of the expected number, not the given number in the line. If the checksum is wrong, then the firmware should not rely on the line being correct, including the N value. The same goes for valid checksum but line number out of sequence, the algorithm as stated will keep requesting the same line!

--Bobc 21:41, 30 July 2012 (UTC)

Other stuff

Ah excellent, I've been waiting for this! I've been working from the gcode and mcode pages in the old wiki which have a few holes.

The line number and checksum stuff is new to me- I'll implement that into my firmware in the coming days. So are some of these M-codes for that matter.

Can we add some sort of reference for what the host expects in response from the firmware? So far, I'm sending back OK when the command is queued or executed and T: nnn every second when the heater is on, which as far as I can tell is all that's needed.

ps: why are G20/G21/G90/G91/G92 specified to block? ("The following commands are not buffered. When one is received it is stored, but it is not acknowledged to the host until the buffer is exhausted and then the command has been executed.") they simply alter the conversion factors for the next command received in my firmware, and so can respond OK immediately.

Only G4 (dwell) and M101 (start extruder when up to temperature, apparently superceded by the new M109) block in my firmware at the moment, and I'm seriously considering making even these queue-able so they block the queue instead of the command download stream.

-- Triffid Hunter


I agree. It's great for this to be documented.

I had one suggestion on the checksum -- it should perhaps use a stronger CRC checksum, and should also encorporate the length as well? Is the N and * part of an external standard, or a RepRap special sauce?

If they are RepRap specific, I'd suggest changing the N code to include line length as something like "N101.50" for line 101, consisting of 50 characters.

I use the following CRC algorithm, which I believe I stole from the CCITT standard:

static inline uint16_t GetCRC( uint16_t crc, char ser_data )
{
  crc  = (unsigned char)(crc >> 8) | (crc << 8);
  crc ^= ser_data;
  crc ^= (unsigned char)(crc & 0xff) >> 4;
  crc ^= (crc << 8) << 4;
  crc ^= ((crc & 0xff) << 4) << 1;
  return crc;
}

The logic to compute checksum would then become:

uint16_t cs = 0;
for(int i = 0; i < cmd.length(); i++)
  cs = GetCRC( cs, cmd.charAt(i) );

computedCrc = cs;

So, the full logic for accepting or testing a line, encoded with full N and CRC checksum would be something like:

// was line number and checksum provided?
bool value = true;
if( lineNumber != 0 )
{
  valid = lineNumber == expectedLineNumber
    && cmd.length() == providedLength
    && computedCrc == providedCrc;
}

// accept or reject the line based on valid flag

This does add a few bytes of overhead (3-4 for length, 2-3 for 16 bit crc), but may be worth it allows you to run a higher baud rate with reasonably low error rates -- the odds of a false positive are near enough to zero to make any statistician happy.

-- BeagleFury

Just wanted to chime in - Thanks Adrian! This answers many questions for me! -- Wade

what part of the line does cmd.length() refer to?

Just trying to implement the checksum logic, and realised that it makes no sense for the checksum to include itself or things get very recursive. What point is considered end-of-line? is it the asterisk? the space before the asterisk? the last non-whitespace before the asterisk?

My firmware doesn't buffer the line, rather processes it character by character so this has to become another special case.

-- Triffid Hunter

The checksum includes all characters in the string up to and including the character before the asterisk (i.e. up to but not including the asterisk). -- neilrqm

Future-proof M-codes?

Adding new M-codes for extra sensors/heaters seems a little non-future-proof to me. My firmware uses P parameter to know which sensor/heater is being referred to eg M104 S100 sets heater 0 to 100c, but M104 P2 S100 sets heater 2 to 100c. Same for all the temperature sensor readback stuff. Future proofing protocols is always a good idea :)

G91: Set to Relative Positioning

Example: G91 All coordinates from now on are relative to the last position.

Question: does this include the feed rate?

-- User:Pietr

M203: Record Z adjustment

which firmware does this?

Sprinter Main does not have M203 implimented Sprinter Experimental has M203 as "M203 Temperature monitor for Repetier" Repetier has M203 as Temperaturmonitor. Marlin has M203 - Set maximum feedrate that your machine can sustain (M203 X200 Y200 Z300 E10000) in mm/sec Teacup has no M203

Does any current or experimental firmware have the z adjustment implimented?

eMAKER Sprinter used this. but is now deprecated in favour of Marlin.

-- jmgiacalone

M92: Set axis_steps_per_unit

M92 Sets the number of steps per unit, this is GREAT to fine tuning the extruder head, where even different colors of the same filament act differently, even when the measured diameter is measured precisely. It's simple enough to calibrate this using a simple cube alternating layers between 100% infill and 95% infill and adjusting the E steps per mm to not show gaps on the 100% layers and to just barely show gaps on the 95% layers.

M92 is much better for compensating for different filament than putting it in the slicer program, because you might want to run the same program with different colors.. even within the same job, perhaps one would want to pause the program during a non critical infill, remove the filament, put in a different color, and then continue.. if you had previously calibrated all your filaments and got accurate steps per mm of those filaments, you can simply issue a M92 for the filament you just installed, then when you continue the program, the extruder will be working correctly.

The problem I find is that I don't know what number to start putting in there.. it is listed in config.h, however that can be overridden if the eeprom is activated. I notice that M99: Set axis_hysteresis_mm has a corresponding M98: Get axis_hysteresis_mm why not have an M91: Get axis_steps_per_unit. Then there would be no mucking about in code trying to figure out what the extruder is currently set at, and it would make it MUCH easier for people who bought kit machines who really don't understand the code to be able to calibrate the extruder head.

EEPROM gcodes

It would be great if there were such a gcode function since still at the time of writing the retailer at least aught to point the client in the right direction for resources on the subject. Which unfortunately very few seems to actually do and the client remains restrained as a consumer instead of as advertised an step towards a emancipated maker through educational resources on settings/calibration, but also inspirational homage dito, to use the tool efficiently as well as with heart. Thankfully there are initiatives such as FSF's "Respects Your Freedom hardware product certification", which one can easily endorse especially in times were companies reap but, more importantly do not sow.

Anyhow, there are some Proposed EEPROM configuration codes which marlin, sprinter, teacup et al firmwares uses. But needless to say, all of these depend on that one enabled the feature in the configuration pages and beyond that a friendly GUI, which repetier host is the only alternative (so far) when it comes to "easy to use point and click"-settings.

For Teacup firmware EECONFIG is enabled by default, so there is no need for enabling anything. And you guessed it, quite some retailers have no idea of what they're selling. This is a consequence of RepRap putting so much emphasis on being open source ( = zero pay for developers) and cheering commercial shops ( = all money goes to the shops). So, I see no point in complaining about "retailers". It's what RepRap asks for. --Traumflug 12:07, 6 December 2012 (UTC)

Time for G-code V2

Is it time to rewrite this G-code specification, maybe call it version 2, or a more creative naming variant? The current specification is a kludge going back many years and authors. The ACK specification is inconsistent. There is no formal language specification, so new language features get added and "do their best to follow existing standards" - standards which aren't actually defined. Different firmwares provide variants on the specification here, but again there's no standard for them to follow, or way to define their variant so control software programmers can adjust easily and confidently.

  1. Let's discuss a roadmap and milestones for such an effort.
  2. Let's create a specification in a formalized notation so non-english speakers don't need a translator to read it.
  3. Let's formalize our 3D printer G-code variant by writing it in Backus–Naur Form. Indeed this may scare some cooks out of the kitchen...I doubt it...but if they are, maybe that's good.
  4. Let's get a standard and consistent ACK
  5. Let's discuss and find ways to improve the ACK to make things easier for control software
  6. Let's not leave slots for "forwards compatibility". Instead, let's recommend (or specify) how to extend the specification we create.
  7. Let's create a consistent ACK specification. The current one is inconsistent. Take, for example, the wait commands. Rather than send an OK as response to the command, the spec. allows firmwares to send other data - such as the current temp readings (w/targets) - and it can easily take up to 600 seconds for control software to receive "OK" while it was processing kilobytes of response data.
  8. Let's address how commands are buffered. For example, it might make sense to specify that upon receiving a buffered command, an ACK is sent in response that indicates the command was buffered - or more importantly which command was buffered.
  9. Let's create a standard way for firmwares to identify themselves, and their capabilities.

Here's a G-Code example per this spec. from Marlin that exposes fundamental issues:

Send: M104 S1900
Recv: ok T:28.1 /1900.0 B:59.8 /60.0 @:127 B@:0
Recv: ok T:29.2 /1900.0 B:59.9 /60.0 @:127 B@:0
Recv: ok T:31.3 /1900.0 B:59.9 /60.0 @:127 B@:0
Recv: ok T:32.0 /1900.0 B:60.0 /60.0 @:127 B@:0
...
...
Error:0
: Extruder switched off. MAXTEMP triggered !
Error: Printer stopped deu to errors. Fix the error and use M999 to restart!. (Temperature is reset. Set it before restarting)

A similar scenario is encountered when setting the bed temp. According to the spec we expect a similar result for a target < MINTEMP - possibly permuting this (poor) specification outcome to at least 4 use-cases.

The command M104 S1900 asks the printer to destroy a typical reprap hotend. It would be trivial to specify how to respond with an error msg. for an out-of-range temp. request immediately, not when hitting MAXTEMP. Same for MINTEMP if that's the case. However, the current spec. does not provide a way to ACK with a standard error msg. In fact, it does not provide a standard ACK format, it just illustrates what certain firmwares do in their ACKs.