diff --git a/docs/protocol-documentation.md b/docs/protocol-documentation.md index bd5dc1c..fde0f88 100644 --- a/docs/protocol-documentation.md +++ b/docs/protocol-documentation.md @@ -789,9 +789,10 @@ Server version and name. | id | [uint32](#uint32) | | Line ID. Numeric ID, starting from 1, that is unique to each line in the track. This ID is used to address the line in other requests. | | name | [string](#string) | | Configured line name. This name is otherwise unused by the API, and is provided to the client for end-user convenience. | | axes | [uint32](#uint32) | | Total number of axes in the line. | -| axis_length | [float](#float) | | Length of each axis in the line, in meters. | -| carrier_length | [float](#float) | | Carrier magnet length, in meters. | +| axis_length | [float](#float) | | Length of each axis in the line, in millimeters. | +| carrier_length | [float](#float) | | Carrier dimension parallel to carrier movement, in millimeters. | | drivers | [uint32](#uint32) | | Total number of drivers in the line. | +| carrier_width | [float](#float) | | Carrier dimension perpendicular to carrier movement, in millimeters. | diff --git a/protobuf/mmc/core.proto b/protobuf/mmc/core.proto index f576afd..df98a46 100644 --- a/protobuf/mmc/core.proto +++ b/protobuf/mmc/core.proto @@ -49,12 +49,14 @@ message Response { string name = 2; // Total number of axes in the line. uint32 axes = 3; - // Length of each axis in the line, in meters. + // Length of each axis in the line, in millimeters. float axis_length = 4; - // Carrier magnet length, in meters. + // Carrier dimension parallel to carrier movement, in millimeters. float carrier_length = 5; // Total number of drivers in the line. uint32 drivers = 6; + // Carrier dimension perpendicular to carrier movement, in millimeters. + float carrier_width = 7; } // All configured lines in track. repeated Line lines = 1; diff --git a/site/protocol-documentation.html b/site/protocol-documentation.html index 396bbbc..86bb962 100644 --- a/site/protocol-documentation.html +++ b/site/protocol-documentation.html @@ -3294,13 +3294,13 @@

Response.TrackConfig.Line

axis_length float -Length of each axis in the line, in meters. +Length of each axis in the line, in millimeters. carrier_length float -Carrier magnet length, in meters. +Carrier dimension parallel to carrier movement, in millimeters. drivers @@ -3308,6 +3308,12 @@

Response.TrackConfig.Line

Total number of drivers in the line. + +carrier_width +float + +Carrier dimension perpendicular to carrier movement, in millimeters. +

diff --git a/site/search/search_index.js b/site/search/search_index.js index 15a881e..85ad345 100644 --- a/site/search/search_index.js +++ b/site/search/search_index.js @@ -1 +1 @@ -var __index = {"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"],"fields":{"title":{"boost":1000.0},"text":{"boost":1.0},"tags":{"boost":1000000.0}}},"docs":[{"location":"index.html","title":"PMF MMC system","text":"

PMF provides the Motion Motor Control (MMC) system for controlling Linear Motor Systems (LMS) with ease and high precision.

"},{"location":"index.html#getting-started","title":"Getting started","text":""},{"location":"index.html#mmc-server","title":"MMC Server","text":"

The MMC Server acts as an endpoint that allows multiple clients to interface with the LMS. The server must run on a PC connected to the first driver of the LMS. Contact our engineers to obtain the MMC Server files and organize them as follows:

mmc-server\n\u251c\u2500 config.json5\n\u251c\u2500 mmc.exe\n\u2514\u2500 mmc.pdb\n
Navigate to the mmc-server folder and run the executable:
mmc.exe --log_level=info\n

"},{"location":"index.html#mmc-api","title":"MMC-API","text":"

Our API is built with Protobuf, offering cross-language compatibility to support your programming language of choice. To integrate our API into your program, ensure your working environment supports Protobuf. For complete integration instructions, see the MMC-API Guidelines page.

"},{"location":"index.html#conventions","title":"Conventions","text":"

This section defines the terminology used throughout the PMF MMC documentation.

"},{"location":"index.html#system-hierarchy","title":"System Hierarchy","text":"

The following terms apply to the PMF MMC system:

"},{"location":"index.html#id-constraints","title":"ID Constraints","text":"

Important: ID Indexing

All system IDs (Lines, Drivers, Axes, and Carriers) use 1-based indexing. The first ID is always 1.

Entity Max ID Calculation / Notes Line 256 Maximum number of lines supported per track. Driver 256 Maximum number of drivers per line. Axis 768 Based on 256 drivers \u00d7 3 axes per driver. Carrier 768 Maximum number of moveable magnets per line."},{"location":"changelog.html","title":"Changelog","text":"

All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

"},{"location":"changelog.html#200-2026-03-16","title":"2.0.0 - 2026-03-16","text":""},{"location":"changelog.html#added","title":"Added","text":""},{"location":"changelog.html#changed","title":"Changed","text":""},{"location":"changelog.html#removed","title":"Removed","text":""},{"location":"changelog.html#fixed","title":"Fixed","text":""},{"location":"changelog.html#121-2026-01-21","title":"1.2.1 - 2026-01-21","text":""},{"location":"mmc-api.html","title":"MMC-API Guidelines","text":"

This page covers how to use MMC-API to operate on LMS connected to PMF's MMC system.

"},{"location":"mmc-api.html#mmc-api-structure","title":"MMC-API Structure","text":"

The MMC API consists of three categories: core, command, and info. Each category contains corresponding requests and responses. Please refer to the protocol documentation page for the expected response for each request.

"},{"location":"mmc-api.html#mmc-core","title":"MMC Core","text":"

Use MMC core messages to retrieve server information and track configuration. PMF recommends that clients verify compatibility with the server API version before operation. Starting from version 2.0.0, breaking changes may occur between major versions, therefore clients must ensure they are compatible with the server's API version. Mismatched versions may result in invalid requests or undefined behavior. Clients must fetch the track configuration prior to operating the PMF MMC system to ensure all messages passed to the server contain valid parameters. Refer to the MMC core documentation for a comprehensive list of message types and expected responses.

"},{"location":"mmc-api.html#mmc-command","title":"MMC Command","text":"

Use MMC command messages to operate the PMF MMC system. Clients must use the following rules when sending MMC command messages.

Monitor command status via the command info request defined in the MMC Info section. A list of commands are available on MMC command documentation.

"},{"location":"mmc-api.html#mmc-info","title":"MMC Info","text":"

Use MMC info messages to monitor the real-time state of the track and command status. The client can specify which track information to request by enabling the relevant flags within the track info message definition. The API also allows filtering track info based on driver range, axis range, or specific carrier IDs. Refer to the MMC info documentation for the complete message definitions used to request track and command states.

"},{"location":"mmc-api.html#create-request","title":"Create Request","text":"

This section demonstrates how to construct and encode a request for transmission. The first example illustrates how to decode and validate a response before use. Subsequent examples will omit the response processing logic to focus on request creation and key considerations for specific commands.

Info

Client must exclusively use the mmc.Request message type to send requests to the server. The server always returns an mmc.Response message to be decoded on client side. Any other message sent to server will return mmc.Response.request_error, showing the message is invalid.

"},{"location":"mmc-api.html#requesting-core-information","title":"Requesting Core Information","text":"

Info

A core request message contains only one enum field. The following example demonstrates how to request the API version used by the server. Other core requests are implemented in the same manner.

Warning

Sending a core request with kind CORE_REQUEST_KIND_SERVER_INFO will always return mmc.Response.core.request_error.

zigpython

Tip

Zig users can directly use the pmotionf/mmc-api repository for ease of integration. If you are using a different Zig version, generate the Zig files from the source Protobuf files using zig-protobuf library.

const api = @import(\"mmc-api\");\n// Create a request and encode the message. Encode with passing the\n// transport writer interface pointer and allocator. Send the message by \n// flush the writer..\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .core = .{ .kind = .CORE_REQUEST_KIND_SERVER_INFO },\n    },\n};\ntry request.encode(&writer.interface, allocator);\ntry writer.interface.flush();\n// Receive and decode the message by passing the reader interface pointer \n// and allocator.\nconst decoded: api.protobuf.mmc.Response = try .decode(\n    &client.reader.interface,\n    client.allocator,\n);\nswitch (decoded.body orelse std.log.err(\"Invalid Response\",.{})) {\n    .core => |core_resp| switch (core_resp.body orelse\n        std.log.err(\"Invalid Response\",.{})) {\n        .server => |server| std.log.info(\n              \"Server API version: {}.{}.{}\",\n              .{server.api.major, server.api.minor, server.api.patch,}\n          ),\n          .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n          else => std.log.err(\"Invalid Response\",.{}),\n    },\n    .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n    else => std.log.err(\"Invalid Response\",.{}),\n};\n
import mmc_pb2 as mmc\n\n# Snipped: Create and connect socket to server\n\n# Create a request message\nrequest = mmc.Request()\nrequest.core.kind = mmc.mmc_dot_core__pb2.Request.CORE_REQUEST_KIND_SERVER_INFO\n\n# Snipped: Send and receive the message\n\n# Parse response\nmsg = mmc.Response()\nmsg.ParseFromString(response)\n\n# Validate and use the response accordingly\nif msg.WhichOneof(\"body\") == \"request_error\":\n    print(\"Error: \", mmc.Request.Error.Name(msg.request_error))\nelif msg.WhichOneof(\"body\") == \"core\":\n    # Validate if the core response that we receive is `api_version`\n    if msg.core.WhichOneof(\"body\") == \"request_error\":\n        print(\n            \"Error: \",\n            mmc.mmc_dot_core__pb2.Request.Error.Name(msg.core.request_error),\n        )\n    elif msg.core.WhichOneof(\"body\") == \"server\":\n        api = msg.core.server.api\n        print(\n            f\"Server API Version: {api.major}.{api.minor}.{api.patch}\"\n      )\n    else:\n        print(\"Invalid Response\")\nelse:\n    print(\"Invalid Response\")\n\ns.close()\n
"},{"location":"mmc-api.html#command-request","title":"Command Request","text":"

Mandatory Command Cleanup

Every command request returns a unique Command ID. The client is required to:

  1. Track the command status using this ID.
  2. Invoke remove_command once the state reaches COMPLETED or FAILED.

Failure to remove finished commands will block the server queue and prevent further command execution.

Check Error Reason

If the command status is FAILED, users can find a descriptive reason by checking the command's error field.

"},{"location":"mmc-api.html#initialize-carrier","title":"Initialize Carrier","text":"

Info

A carrier must be initialized before any actions can be performed. The initialize command is one of many available methods for initializing carriers. This command is sent to the axis specified by the axis parameter.

Unique Carrier ID Requirement

The client must ensure the carrier_id is unique across the entire line. If the ID is already in use by another initialized carrier on the same line, the server will return CONFLICTING_CARRIER_ID.

Example

The following request initializes an uninitialized carrier with ID 1 on the first line in the forward direction. This carrier's position is on top of axis 1 and axis 2.

zigpython
const api = @import(\"mmc-api\");\n\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .initialize = .{\n                    .line = 1,\n                    .axis = 2,\n                    .carrier = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .link_axis = .DIRECTION_FORWARD,\n                },\n            },\n        },\n    },\n};\n// Snipped content: \n// - Send `initialize` command\n// - Receive command ID as the response of command request\n// - Track command state until state `COMPLETED`\n// - Send `remove_command` command\n// - Receive `removed_id` response as the response of `remove_command` request\n
import mmc_pb2 as mmc\n\n# Creating a request message\nCommand = mmc.mmc_dot_command__pb2.Request()\nrequest = mmc.Request()\nrequest.command.initialize.line = 1\nrequest.command.initialize.axis = 2\nrequest.command.initialize.carrier = 1\nrequest.command.initialize.direction = Command.Direction.DIRECTION_FORWARD\nrequest.command.initialize.link_axis = Command.Direction.DIRECTION_BACKWARD\n# Snipped content: \n# - Send `initialize` command\n# - Receive command ID as the response of command request\n# - Track command state until state `COMPLETED`\n# - Send `remove_command` command\n# - Receive `removed_id` response as the response of `remove_command` request\n
"},{"location":"mmc-api.html#auto-initialize-carriers","title":"Auto Initialize Carriers","text":"

Info

Auto initialize all carriers on the specified lines simultaneously. This process operates on carrier clusters, where a cluster is defined as a group of uninitialized carriers located on adjacent axis.

Warning

Each cluster requires at least one free axis to successfully perform the auto-initialization. Any cluster lacking a free axis will be ignored, and all carriers within that cluster will remain uninitialized upon command completion.

Tip

Ignore the acceleration and velocity fields to use the default values. The default value are:

Example

Auto initialize all carriers on line 1 and line 2.

zigpython
const api = @import(\"mmc-api\");\n\n// Allocate lines\nvar lines: std.ArrayList(\n    api.protobuf.mmc.command.Request.AutoInitialize.Line,\n) = .empty;\ndefer lines.deinit(allocator);\n\n// Define first line\ntry lines.append(allocator, .{\n    .line = 1,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Define second line\ntry lines.append(allocator, .{\n    .line = 2,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .auto_initialize = .{\n                    .lines = lines,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n\n# Define first line\nline1 = Command.AutoInitialize.Line()\nline1.line = 1\nline1.velocity = 600\nline1.acceleration = 6000\n\n# Define second line\nline2 = Command.AutoInitialize.Line()\nline2.line = 2\nline2.velocity = 600\nline2.acceleration = 6000\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.auto_initialize.lines.append(line1)\nrequest.command.auto_initialize.lines.append(line2)\n
"},{"location":"mmc-api.html#deinitialize-carriers","title":"Deinitialize Carriers","text":"

Info

Deinitialize will release motor control on the specified carriers and remove carrier states from MMC system. Deinitialize all carriers on a line by not specifying a target. If a target is specified, carriers are deinitialized based on that target:

Example

Deinitialize carrier 1 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .deinitialize = .{\n                    .line = line.id,\n                    .target = .{ .carrier = 1 }\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.deinitialize.line = 1\nrequest.command.deinitialize.carrier = 1\n
"},{"location":"mmc-api.html#move-carrier","title":"Move Carrier","text":"

Tip

Track the carrier state until it reaches MOVE_COMPLETED before sending further commands to the specified carrier to avoid unwanted behavior. The command state COMPLETED only indicates that the command was successfully received and is being processed by the MMC system.

Warning

The target field must be specified by the user, and only the last target value will be serialized to the server. See Oneof for complete a description on Oneof protobuf type.

Example

Move initialized carrier 1 to axis 3 on the second line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .move = .{\n                    .line = 2,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .target = .{.axis = 3},\n                    .control = .CONTROL_POSITION,\n                    .disable_cas = false,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.move.line = 2\nrequest.command.move.carrier = 1\nrequest.command.move.velocity = 1000\nrequest.command.move.acceleration = 6000\nrequest.command.move.axis = 3\n# mmc.Control() message is not generated by protoc compiler because Python does\n# not allow to use definition based on namespace.\n# 1 for CONTROL_POSITION\n# 2 for CONTROL_VELOCITY.\nrequest.command.move.control = 1\nrequest.command.move.disable_cas = False\n
"},{"location":"mmc-api.html#push","title":"Push","text":"

Info

Forcefully moves an initialized carrier on the specified axis by one carrier length. Use this movement to cross a line boundary, which deinitializes the carrier from the current line upon completion.

If the carrier field is provided in the push command, the axis enters a pushing state. In this state, the axis remains busy and waits for the specified carrier to arrive; once it arrives, the axis automatically pushes the carrier.

Warning

When pushing the carrier to a different line, the receiving axis on the destination line must be in a pulling state.

Tip

To disable the pushing state on an axis, utilize the stop push command.

Example

Push carrier on axis 1 of line 2 backward to line 1.

Warning

The destination axis on line 1 must be in pulling state.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .push = .{\n                    .line = 2,\n                    .axis = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.push.line = 2\nrequest.command.push.axis = 1\nrequest.command.push.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.push.velocity = 1000\nrequest.command.push.acceleration = 6000\n
"},{"location":"mmc-api.html#pull","title":"Pull","text":"

Info

Initialize an incoming carrier located outside the current line. This command puts the specified axis into pulling state. This initialization procedure has the following behavior:

Example

Set axis 6 of line 1 to pulling state, and move the pulled carrier to axis 3.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pull = .{\n                    .line = 1,\n                    .axis = 6,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .direction = .DIRECTION_BACKWARD,\n                    .transition = .{\n                        .control = .CONTROL_POSITION,\n                        .disable_cas = false,\n                        .target = .{.axis = 3},\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.pull.line = 1\nrequest.command.pull.axis = 6\nrequest.command.pull.carrier = 1\nrequest.command.pull.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.pull.velocity = 1000\nrequest.command.pull.acceleration = 6000\nrequest.command.pull.transition.control = 1\nrequest.command.pull.transition.disable_cas = False\nrequest.command.pull.transition.axis = 3\n
"},{"location":"mmc-api.html#release-carrier","title":"Release Carrier","text":"

Info

Put the initialized carrier into the NONE state, allowing it to be moved manually or by external systems.

Example

Release control of carrier 1 on line 1.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .release = .{\n                    .line = 1,\n                    .target = .{.carrier = 1},\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.release.line = 1\nrequest.command.release.carrier = 1\n
"},{"location":"mmc-api.html#calibrate-line","title":"Calibrate Line","text":"

Info

To calibrate the drivers' configuration on a line, an uninitialized carrier must be located at the center of the first axis

Example

Calibrate the drivers' configuration on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .calibrate = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.calibrate.line = 1\n
"},{"location":"mmc-api.html#stop-push","title":"Stop Push","text":"

Tip

To reset pushing state on all axis, ignore the axes field.

Example

Reset the pushing state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_push = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_push.line = 1\nrequest.command.stop_push.axes.start = 1\nrequest.command.stop_push.axes.end = 4\n
"},{"location":"mmc-api.html#stop-pull","title":"Stop Pull","text":"

Tip

To reset the pulling state on all axes, omit the axes field.

Example

Reset the pulling state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_pull = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_pull.line = 1\nrequest.command.stop_pull.axes.start = 1\nrequest.command.stop_pull.axes.end = 4\n
"},{"location":"mmc-api.html#set-carrier-id","title":"Set Carrier ID","text":"

Warning

The carrier ID of each carrier must be unique within a line.

Example

Change the carrier ID of carrier 1 to 4 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_carrier_id = .{\n                    .line = 1,\n                    .carrier = 1,\n                    .new_carrier = 4,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_carrier_id.line = 1\nrequest.command.set_carrier_id.carrier = 1\nrequest.command.set_carrier_id.new_carrier = 4\n
"},{"location":"mmc-api.html#set-zero","title":"Set Zero","text":"

Example

Set the zero point of the first line.

Warning

An initialized carrier must be located on the first axis of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_zero = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_zero.line = 1\n
"},{"location":"mmc-api.html#clear-errors","title":"Clear Errors","text":"

Warning

Always clear errors whenever an error is detected on an axis or driver. Failing to clear errors may result in unwanted behavior.

Tip

Ignore the axes field to clear errors on all drivers and axes on the line.

Example

Clear all errors on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .clear_errors = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.clear_errors.line = 1\n
"},{"location":"mmc-api.html#emergency-stop","title":"Emergency Stop","text":"

Tip

Pass an empty list to stop operations on all lines.

Example

Stop operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop.lines.extend([])\n
"},{"location":"mmc-api.html#pause-execution","title":"Pause Execution","text":"

Tip

Pass empty list to pause operations on all lines.

Example

Pause operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pause = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.pause.lines.extend([])\n
"},{"location":"mmc-api.html#resume-execution","title":"Resume Execution","text":"

Tip

Pass an empty list to resume operation on all lines.

Example

Resume operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .@\"resume\" = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.resume.lines.extend([])\n
"},{"location":"mmc-api.html#remove-command","title":"Remove Command","text":"

Warning

Failure to remove a command will block the queue and prevent the server from accepting further commands.

Tip

Always check the command status after sending a command message. (Request Command State)

Example

Remove the command with ID 1 from the server.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .remove_command = .{.command = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Creating a request message\nrequest = mmc.Request()\nrequest.command.remove_command.command = id\n
"},{"location":"mmc-api.html#info-request","title":"Info Request","text":""},{"location":"mmc-api.html#request-command-state","title":"Request Command State","text":"

Example

Wait till the command state becomes COMPLETED or FAILED, then remove the command.

zigpython
const api = @import(\"mmc-api\");\n\nfn waitCommand(id: u32) !void {\n    defer removeCommand(id);\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .command = .{ .id = id },\n                },\n            },\n        },\n    };\n    while (true) {\n        try request.encode(&writer.interface, allocator);\n        try writer.interface.flush();\n        var decoded: api.protobuf.mmc.Response = try .decode(\n            &reader.interface,\n            allocator,\n        );\n        defer decoded.deinit(allocator);\n        const command_response = switch (decoded.body orelse\n            return error.InvalidResponse) {\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n                return;\n            },\n            .info => |info_resp| switch (info_resp.body orelse\n                return error.InvalidResponse) {\n                .command => |commands_resp| commands_resp.items.items[0],\n                .request_error => |req_err| {\n                    std.log.err(\"{t}\", .{req_err});\n                    return;\n                },\n                else => return error.InvalidResponse,\n            },\n            else => return error.InvalidResponse,\n        };\n        switch (command_response.status) {\n            .COMMAND_STATUS_PROGRESSING => {}, // continue the loop\n            .COMMAND_STATUS_COMPLETED => return,\n            .COMMAND_STATUS_FAILED => {\n                std.log.err(\"{t}\", .{command_response.@\"error\".?});\n                return;\n            },\n            .COMMAND_STATUS_UNSPECIFIED => return error.InvalidResponse,\n        }\n    }\n}\n
import mmc_pb2 as mmc\n\ndef waitCommand(id):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.command.id = id\n    while True:\n        # Send and receive response\n        s.sendall(request.SerializeToString())\n        response = s.recv(4096)\n\n        # Parsing the response\n        msg = mmc.Response()\n        msg.ParseFromString(response)\n        Command = mmc.mmc_dot_info__pb2.Response.Command()\n\n        # Validate and use the response accordingly\n        if msg.WhichOneof(\"body\") == \"request_error\":\n            print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n            return\n        elif msg.WhichOneof(\"body\") == \"info\":\n            # Validate if the core response that we receive is `api_version`\n            if msg.info.WhichOneof(\"body\") == \"request_error\":\n                print(\n                    \"Request Error\",\n                    mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n                )\n                return\n            elif msg.info.WhichOneof(\"body\") == \"command\":\n                command = msg.info.command.items[0]\n                if command.status == Command.Status.COMMAND_STATUS_COMPLETED:\n                    removeCommand(id)\n                    return\n                elif command.status == Command.Status.COMMAND_STATUS_FAILED:\n                    removeCommand(id)\n                    raise Exception(Command.Error.Name(command.error))\n                else:\n                    print(\"Invalid Response\")\n                    return\n            else:\n                print(\"Invalid Response\")\n                return\n        else:\n            print(\"Invalid Response\")\n            return\n
"},{"location":"mmc-api.html#request-track-state","title":"Request Track State","text":"

Tip

Certain commands require the client to monitor carrier status to ensure movement is completed.

Warning

Monitor the error flags of driver, axis and carriers to prevent damage to the motor or driver board. Pay close attention to inverter_overheat on the driver and overcurrent flags on the axis; immediately deinitialize any carrier on the affected axes and drivers if these are detected. The overvoltage and undervoltage flags indicate that the system voltage supply may have a problem; please consult with our engineers to resolve the issue.

Request carrier state

Tip

zigpython
const api = @import(\"mmc-api\");\nfn carrierState(line: u32, carrier: u32) !void {\n    var carrier_id = [1]u32{carrier};\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .track = .{\n                        .line = line,\n                        .info_carrier_state = true,\n                        .filter = .{\n                            .carriers = .{\n                                .ids = .fromOwnedSlice(&carrier_id),\n                            },\n                        },\n                    },\n                },\n            },\n        },\n    };\n    try request.encode(&writer.interface, allocator);\n    try writer.interface.flush();\n    var decoded: api.protobuf.mmc.Response = try .decode(\n        &reader.interface,\n        allocator,\n    );\n    defer decoded.deinit(allocator);\n    switch (decoded.body orelse return error.InvalidResponse) {\n        .info => |info_resp| switch (info_resp.body orelse\n            return error.InvalidResponse) {\n            .track => |track_resp| {\n                std.log.info(\"{}\", .{track_resp.carrier_state.items[0]});\n            },\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n            },\n            else => return error.InvalidResponse,\n        },\n        .request_error => |req_err| {\n            std.log.err(\"{t}\", .{req_err});\n            return;\n        },\n        else => return error.InvalidResponse,\n    }\n}\n
import mmc_pb2 as mmc\ndef carrierState(line, carrier):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.track.line = line\n    request.info.track.info_carrier_state = True\n    request.info.track.carriers.ids.append(carrier)\n\n    # Parsing the response\n    msg = mmc.Response()\n    msg.ParseFromString(response)\n    # Validate and use the response accordingly\n    if msg.WhichOneof(\"body\") == \"request_error\":\n        print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n    elif msg.WhichOneof(\"body\") == \"info\":\n        # Validate if the core response that we receive is `api_version`\n        if msg.info.WhichOneof(\"body\") == \"request_error\":\n            print(\n                \"Request Error\",\n                mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n            )\n        elif msg.info.WhichOneof(\"body\") == \"track\":\n            assert len(msg.info.track.carrier_state) != 0\n            carrier = msg.info.track.carrier_state[0]\n            print(carrier)\n        else:\n            print(\"Invalid Response\")\n    else:\n        print(\"Invalid Response\")\n
"},{"location":"protocol-documentation.html","title":"Protocol Documentation","text":""},{"location":"protocol-documentation.html#table-of-contents","title":"Table of Contents","text":"

Top

"},{"location":"protocol-documentation.html#mmcproto","title":"mmc.proto","text":""},{"location":"protocol-documentation.html#request","title":"Request","text":"

Request message. All client-to-server messages should be of this message type.

Field Type Label Description core core.Request Core request. Used to retrieve information about the server or the configured track. command command.Request Command request. Used to send and manage commands to the server, which will execute commands on the connected track. info info.Request Info request. Used to retrieve information about track state or commands processed by the server.

"},{"location":"protocol-documentation.html#response","title":"Response","text":"

Response message. All server-to-client messages will be of this message type.

Field Type Label Description core core.Response Core response. command command.Response Command response. info info.Response Info Response. request_error Request.Error Top-level request error. This error field will be returned only if the top-level request could not be handled properly. Otherwise, response kinds may contain more specific error codes.

"},{"location":"protocol-documentation.html#requesterror","title":"Request.Error","text":"Name Number Description MMC_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. MMC_REQUEST_ERROR_INVALID_MESSAGE 1 The request could not be decoded as a valid protobuf message.

Top

"},{"location":"protocol-documentation.html#rangeproto","title":"range.proto","text":""},{"location":"protocol-documentation.html#range","title":"Range","text":"Field Type Label Description start uint32 Start of range, inclusive. end uint32 End of range, inclusive.

Top

"},{"location":"protocol-documentation.html#mmccommandproto","title":"mmc/command.proto","text":""},{"location":"protocol-documentation.html#request_1","title":"Request","text":"

Command API: List of commands to operate the PMF's motion system.

When a command is sent to the server, it will be queued for execution. Command execution status can be polled through the Info API. The status remains stored in a limited history buffer, and should be cleared with remove_command after completion.

Field Type Label Description calibrate Request.Calibrate Calibrate a line. This command only needs to be run once after hardware setup; calibrated values will remain stored in drivers even after a power cycle. set_zero Request.SetZero Set the zero position of the specified line. This command can be run optionally after calibration, upon which all drivers will store the set zero position of the line. The set zero position will remain unchanged even after a power cycle. initialize Request.Initialize Initialize a carrier. Carriers must be initialized before they can be moved. Initialization is required after every power cycle. auto_initialize Request.AutoInitialize Initialize all carriers of the specified line(s). If no lines are specified, initialize all carriers across all lines in the track. deinitialize Request.Deinitialize Deinitialize a carrier. This removes all carrier information, such as recognized position and carrier ID. move Request.Move Move an initialized carrier to the desired position. pull Request.Pull Pull and initialize a new carrier into a line. push Request.Push Push an initialized carrier to the specified direction. stop_pull Request.StopPull Stop waiting to pull a new carrier at an axis. stop_push Request.StopPush Stop waiting to push an initialized carrier at an axis. release Request.Release Release the motor control of a carrier. clear_errors Request.ClearErrors Clear all errors within the specified driver range. remove_command Request.RemoveCommand Cancel a running command or remove its status history. stop Request.Stop Activate emergency stop for all drivers in line(s). Emergency stop will cause all carriers to decelerate to rest, then reset all carriers' movement commands. pause Request.Pause Activate pause for all drivers in line(s). Pause will cause all carriers to decelerate to rest. On resume, the carriers will continue their previously assigned movement commands. resume Request.Resume Deactivate emergency stop and pause for all drivers in line(s). set_carrier_id Request.SetCarrierId Change an existing carrier ID to a new unique carrier ID.

"},{"location":"protocol-documentation.html#requestautoinitialize","title":"Request.AutoInitialize","text":"

Automatically initialize carriers on every specified lines.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines Request.AutoInitialize.Line repeated

"},{"location":"protocol-documentation.html#requestautoinitializeline","title":"Request.AutoInitialize.Line","text":"Field Type Label Description line uint32 Line ID. velocity float optional Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s (default 600 mm/s). acceleration float optional Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2 (default 6000 mm/s^2)."},{"location":"protocol-documentation.html#requestcalibrate","title":"Request.Calibrate","text":"

Calibrate a line by positioning an uninitialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requestclearerrors","title":"Request.ClearErrors","text":"

Clear all error information on the driver. If a target is specified, clear error information of drivers included in that target. If not, clear error information on all drivers of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. drivers Range Driver ID range. axes Range Axis ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestdeinitialize","title":"Request.Deinitialize","text":"

Clear carrier information located on the axis. If a target is specified, clear information of carriers included in that target. If not, clear all carrier information of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range Axis ID range. drivers Range Driver ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestinitialize","title":"Request.Initialize","text":"

Initialize a carrier.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the new carrier. direction Request.Direction Initialization direction for the new carrier. link_axis Request.Direction optional Linked axis direction from the specified axis.

"},{"location":"protocol-documentation.html#requestmove","title":"Request.Move","text":"

Move a carrier to the desired position.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. axis uint32 Move carrier to the center of the axis. location float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. distance float Move carrier to relative distance to current carrier position. Negative distance moves the carrier backwards. control mmc.Control Control method for moving carrier. disable_cas bool Disable the carrier's collision avoidance system (CAS).

"},{"location":"protocol-documentation.html#requestpause","title":"Request.Pause","text":"

Pause any operation in PMF LMS. Any queued commands in the server will be continued once the resume command is given.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, pause operations only on the specified lines.

"},{"location":"protocol-documentation.html#requestpull","title":"Request.Pull","text":"

Pull and initialize a new carrier into a line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the incoming carrier. direction Request.Direction The direction from which the incoming carrier is moving. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. When the transition location target is set to NaN, the velocity must be 0. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. When the transition location target is set to NaN, the acceleration must be 0. transition Request.Pull.Transition optional Smoothly transition to carrier movement after pull completion.

"},{"location":"protocol-documentation.html#requestpulltransition","title":"Request.Pull.Transition","text":"Field Type Label Description control mmc.Control Control method for moving carrier. disable_cas bool Disabling the carrier's collision avoidance system (CAS). target float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. Pass NaN to pull carrier without motor control, allowing carrier to be pulled with external force."},{"location":"protocol-documentation.html#requestpush","title":"Request.Push","text":"

Push an initialized carrier to the specified direction.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. direction Request.Direction Direction of carrier movement. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. carrier uint32 optional Carrier ID. If provided, wait for the specified carrier at the axis and push it once the carrier arrives.

"},{"location":"protocol-documentation.html#requestrelease","title":"Request.Release","text":"

Release the control imposed by the motor to the carrier. If a target is specified, all motors included in that target release control. Otherwise, all carriers on the provided line will be released from control.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. axes Range Axis ID range. drivers Range Driver ID range.

"},{"location":"protocol-documentation.html#requestremovecommand","title":"Request.RemoveCommand","text":"

Remove a command on the server if the command ID is specified. If no command ID is specified, remove any commands received by the server. If the commands are still progressing, cancel the command execution.

Expected response: mmc.Response.body.command.body.removed_id (uint32).

Field Type Label Description command uint32 optional Command ID.

"},{"location":"protocol-documentation.html#requestresume","title":"Request.Resume","text":"

Resume lines that have been stopped or paused. If the line is not paused or emergency stopped, this command will succeed without any effect.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, resume operations only to those specified lines.

"},{"location":"protocol-documentation.html#requestsetcarrierid","title":"Request.SetCarrierId","text":"

Change the carrier ID of an existing initialized carrier. If the new carrier ID already exists on the line, returns INVALID_CARRIER.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Target existing initialized carrier ID. new_carrier uint32 New desired carrier ID (unique in line).

"},{"location":"protocol-documentation.html#requestsetzero","title":"Request.SetZero","text":"

Set a zero position of a line by positioning an initialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requeststop","title":"Request.Stop","text":"

Send an emergency stop command to stop any operation in PMF LMS. This command also removes all queued commands in the server.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, stop operations only on the specified lines and remove all commands that targeting those lines.

"},{"location":"protocol-documentation.html#requeststoppull","title":"Request.StopPull","text":"

Stop pulling a carrier to the specified axis. If no axis is provided, then all pending carrier pulls on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#requeststoppush","title":"Request.StopPush","text":"

Stop pushing a carrier from the specified axis. If no axis is provided, then all pending carrier pushes on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#response_1","title":"Response","text":"

Response description to the command API.

Field Type Label Description id uint32 Assigned ID for newly sent command. removed_id uint32 ID of cleared existing command. request_error Request.Error Error during command's execution.

"},{"location":"protocol-documentation.html#requestdirection","title":"Request.Direction","text":"Name Number Description DIRECTION_UNSPECIFIED 0 DIRECTION_BACKWARD 1 DIRECTION_FORWARD 2"},{"location":"protocol-documentation.html#requesterror_1","title":"Request.Error","text":"Name Number Description COMMAND_REQUEST_ERROR_UNSPECIFIED 0 COMMAND_REQUEST_ERROR_INVALID_LINE 1 Attempted to use line ID outside of the configured lines. COMMAND_REQUEST_ERROR_INVALID_AXIS 2 Attempted to use axis ID outside of the configured axes of the line. COMMAND_REQUEST_ERROR_INVALID_DRIVER 3 Attempted to use driver ID outside of the configured drivers of the line. COMMAND_REQUEST_ERROR_INVALID_ACCELERATION 4 Attempted to use acceleration value outside of 1-245. COMMAND_REQUEST_ERROR_INVALID_VELOCITY 5 Attempted to use velocity value outside of 1-60. COMMAND_REQUEST_ERROR_INVALID_DIRECTION 6 Using invalid direction for the command. COMMAND_REQUEST_ERROR_INVALID_LOCATION 7 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_DISTANCE 8 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_CARRIER 9 Attempted to send a command to carrier outside of 1-2048. COMMAND_REQUEST_ERROR_MISSING_PARAMETER 10 A command missing the required parameter. COMMAND_REQUEST_ERROR_COMMAND_NOT_FOUND 11 Attempted to remove or cancel a non-existing command. COMMAND_REQUEST_ERROR_CARRIER_NOT_FOUND 12 Attempted to send command to an uninitialized carrier. COMMAND_REQUEST_ERROR_OUT_OF_MEMORY 14 Server unable to receive new command caused by out of memory. Try Command.Request.remove_command to free the memory. COMMAND_REQUEST_ERROR_MAXIMUM_AUTO_INITIALIZE_EXCEEDED 15 Attempted to run more than 8 auto initialize instance. COMMAND_REQUEST_ERROR_CONFLICTING_CARRIER_ID 16 Attempted to assign a carrier ID that is already used by another carrier on the same line. COMMAND_REQUEST_ERROR_INVALID_COMMAND 17 Command index is out of bounds for the configured command status buffer.

Top

"},{"location":"protocol-documentation.html#mmccontrolproto","title":"mmc/control.proto","text":""},{"location":"protocol-documentation.html#control","title":"Control","text":"

Carrier motor control kind.

Name Number Description CONTROL_UNSPECIFIED 0 CONTROL_POSITION 1 Carrier controlled with position priority. CONTROL_VELOCITY 2 Carrier controlled with velocity priority.

Top

"},{"location":"protocol-documentation.html#mmccoreproto","title":"mmc/core.proto","text":""},{"location":"protocol-documentation.html#request_2","title":"Request","text":"Field Type Label Description kind Request.Kind"},{"location":"protocol-documentation.html#response_2","title":"Response","text":"

Response description to the core API.

Field Type Label Description server Response.Server Server process information. track_config Response.TrackConfig Track configuration. request_error Request.Error Error response if the core request could not be handled.

"},{"location":"protocol-documentation.html#responsesemanticversion","title":"Response.SemanticVersion","text":"Field Type Label Description major uint32 minor uint32 patch uint32"},{"location":"protocol-documentation.html#responseserver","title":"Response.Server","text":"

Server version and name.

Field Type Label Description name string Server name. version Response.SemanticVersion Server implementation version. api Response.SemanticVersion

"},{"location":"protocol-documentation.html#responsetrackconfig","title":"Response.TrackConfig","text":"Field Type Label Description lines Response.TrackConfig.Line repeated All configured lines in track."},{"location":"protocol-documentation.html#responsetrackconfigline","title":"Response.TrackConfig.Line","text":"Field Type Label Description id uint32 Line ID. Numeric ID, starting from 1, that is unique to each line in the track. This ID is used to address the line in other requests. name string Configured line name. This name is otherwise unused by the API, and is provided to the client for end-user convenience. axes uint32 Total number of axes in the line. axis_length float Length of each axis in the line, in meters. carrier_length float Carrier magnet length, in meters. drivers uint32 Total number of drivers in the line."},{"location":"protocol-documentation.html#requesterror_2","title":"Request.Error","text":"Name Number Description CORE_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. CORE_REQUEST_ERROR_REQUEST_UNKNOWN 1 The core request kind was unspecified."},{"location":"protocol-documentation.html#requestkind","title":"Request.Kind","text":"Name Number Description CORE_REQUEST_KIND_UNSPECIFIED 0 This request kind is unused, and should never be sent. It is reserved as the default request kind according to protobuf specification. CORE_REQUEST_KIND_SERVER_INFO 2 Request server process information. This includes the configured server name and server implementation version. CORE_REQUEST_KIND_TRACK_CONFIG 3 Request the configured track information of the server.

Top

"},{"location":"protocol-documentation.html#mmcinfoproto","title":"mmc/info.proto","text":""},{"location":"protocol-documentation.html#request_3","title":"Request","text":"Field Type Label Description command Request.Command Command information request. Get current status of command; necessary to determine if command is currently running, completed, or failed. track Request.Track Track information request. Get current track state information."},{"location":"protocol-documentation.html#requestcommand","title":"Request.Command","text":"

Request for status of specified command ID from the server. If no command ID is provided, then request for status of all commands from the server.

Expected response: mmc.Response.body.info.body.commands

Field Type Label Description id uint32 optional

"},{"location":"protocol-documentation.html#requesttrack","title":"Request.Track","text":"

Request track state information from server. One or more of the info_ flags must be enabled to select the kind of track information desired. A filter may be optionally provided to limit the source of information from the track.

Expected response: mmc.Response.body.info.body.track

Field Type Label Description lines uint32 repeated Line ID(s). Select line(s) from which information will be retrieved. info_driver_state bool Retrieve driver state information. info_driver_errors bool Retrieve driver error information. info_axis_state bool Retrieve axis state information. info_axis_errors bool Retrieve axis errors information. info_carrier_state bool Retrieve carrier state information. drivers Range Retrieve information from driver ID range. Driver information flags will include drivers within this range. Axis information flags will include every axis belonging to the drivers in this range. Carrier information flags will include every carrier currently controlled by one of the drivers in this range. axes Range Retrieve information from axis ID range. Driver information flags will include drivers that contain one of the axes within this range. Axis information flags will include axes within this range. Carrier information flags will include every carrier currently controlled by one of the axes in this range. carriers Request.Track.Ids Retrieve information from carrier IDs. Driver information flags will include drivers that control one of the carriers within this list. Axis information flags will include axes that control one of the carriers within this list. Carrier information flags will include carriers within this list.

"},{"location":"protocol-documentation.html#requesttrackids","title":"Request.Track.Ids","text":"

List of IDs. At least one ID must be provided.

Field Type Label Description ids uint32 repeated

"},{"location":"protocol-documentation.html#response_3","title":"Response","text":"Field Type Label Description command Response.Commands Information for requested command(s). If empty, no matching command(s) was found. track Response.Track Information for requested track state. request_error Request.Error Info request error. This error field will be returned if the provided info request could not be handled properly."},{"location":"protocol-documentation.html#responsecommand","title":"Response.Command","text":"Field Type Label Description id uint32 Command ID. Valid IDs begin from 1, and may be reused after command status is cleared from server history. status Response.Command.Status Command status. error Response.Command.Error optional Command error response, only if the status is COMMAND_STATUS_FAILED."},{"location":"protocol-documentation.html#responsecommands","title":"Response.Commands","text":"Field Type Label Description items Response.Command repeated"},{"location":"protocol-documentation.html#responseline","title":"Response.Line","text":"Field Type Label Description id uint32 Line ID. driver_state Response.Line.Driver.State repeated Driver state information list. Empty if request flag was disabled. driver_errors Response.Line.Driver.Error repeated Driver error information list. Empty if request flag was disabled. axis_state Response.Line.Axis.State repeated Axis state information list. Empty if request flag was disabled. axis_errors Response.Line.Axis.Error repeated Axis error information list. Empty if request flag was disabled. carrier_state Response.Line.Carrier.State repeated Carrier state information list. Empty if request flag was disabled."},{"location":"protocol-documentation.html#responselineaxis","title":"Response.Line.Axis","text":""},{"location":"protocol-documentation.html#responselineaxiserror","title":"Response.Line.Axis.Error","text":"Field Type Label Description id uint32 Axis ID. overcurrent bool Motor overcurrent detected. Motor control released to prevent damage."},{"location":"protocol-documentation.html#responselineaxisstate","title":"Response.Line.Axis.State","text":"Field Type Label Description id uint32 Axis ID. motor_active bool Axis is currently controlling a carrier. waiting_pull bool Axis is waiting to pull carrier. waiting_push bool Axis is waiting to push carrier. carrier uint32 Carrier ID; non-zero if an initialized carrier is on the axis. hall_alarm_back bool Axis back hall alarm is active. Magnet is detected above back hall sensor. hall_alarm_front bool Axis front hall alarm is active. Magnet is detected above front hall sensor."},{"location":"protocol-documentation.html#responselinecarrier","title":"Response.Line.Carrier","text":""},{"location":"protocol-documentation.html#responselinecarrierstate","title":"Response.Line.Carrier.State","text":"Field Type Label Description id uint32 Carrier ID. Will always be non-zero. position float Position of the carrier in line, in meters. axis_main uint32 Carrier's primary axis ID. axis_auxiliary uint32 optional Carrier's auxiliary axis ID, if carrier is on top of two axes. cas_disabled bool Collision avoidance system (CAS) disabled. cas_triggered bool Collision avoidance system (CAS) triggered. Carrier will automatically resume movement when path is clear. state Response.Line.Carrier.State.State Carrier state."},{"location":"protocol-documentation.html#responselinedriver","title":"Response.Line.Driver","text":""},{"location":"protocol-documentation.html#responselinedrivererror","title":"Response.Line.Driver.Error","text":"Field Type Label Description id uint32 Driver ID. control_loop_time_exceeded bool Control loop exceeded maximum loop time. inverter_overheat bool Inverter is overheated. undervoltage bool Driver voltage supply too low. overvoltage bool Driver voltage supply too high. comm_error_prev bool Communication error with previous driver in line. comm_error_next bool Communication error with next driver in line."},{"location":"protocol-documentation.html#responselinedriverstate","title":"Response.Line.Driver.State","text":"Field Type Label Description id uint32 Driver ID. connected bool Connection status between driver and server. busy bool Driver is currently executing a command. motor_disabled bool Driver motor release activated. All driver motors are inactive. stopped bool Driver emergency stop activated. paused bool Driver pause activated."},{"location":"protocol-documentation.html#responsetrack","title":"Response.Track","text":"Field Type Label Description lines Response.Line repeated"},{"location":"protocol-documentation.html#requesterror_3","title":"Request.Error","text":"Name Number Description INFO_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. INFO_REQUEST_ERROR_INVALID_LINE 1 Invalid line ID provided. Ensure that line ID exists in track configuration. INFO_REQUEST_ERROR_INVALID_AXIS 2 Invalid axis ID provided. Ensure that axis ID exists in line. INFO_REQUEST_ERROR_INVALID_DRIVER 3 Invalid driver ID provided. Ensure that driver ID exists in line. INFO_REQUEST_ERROR_MISSING_PARAMETER 4 Request is missing a required parameter. Ensure that at least one of the information flag is selected when requesting track information. INFO_REQUEST_ERROR_COMMAND_NOT_FOUND 5 Attempted to request information from a non-existing command. INFO_REQUEST_ERROR_INVALID_COMMAND 6 Command index is out of bounds for the configured command status buffer. INFO_REQUEST_ERROR_INVALID_CARRIER 7 Attempted to send a command to carrier outside of range."},{"location":"protocol-documentation.html#responsecommanderror","title":"Response.Command.Error","text":"Name Number Description COMMAND_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. COMMAND_ERROR_INVALID_SYSTEM_STATE 1 System state prevented successful command execution. Ensure that all preconditions are met with track info request before sending command. COMMAND_ERROR_INVALID_CARRIER_ID 2 Deprecated. Check COMMAND_REQUEST_ERROR_INVALID_CARRIER on Command.Request.Error. COMMAND_ERROR_DRIVER_DISCONNECTED 3 Driver connection failed while command progressing. COMMAND_ERROR_UNEXPECTED 4 Unexpected command execution error. This is likely an implementation bug; please contact PMF support for assistance. COMMAND_ERROR_CARRIER_NOT_FOUND 5 Target carrier is removed while command progressing. COMMAND_ERROR_CARRIER_ALREADY_INITIALIZED 6 Attempted to initialize an initialized carrier. COMMAND_ERROR_DRIVER_STOPPED 7 Target driver is stopped while command progressing. Consider resume the driver before sending further command. COMMAND_ERROR_INVALID_CARRIER_TARGET 8 Carrier targeting a location outside of the configured track. COMMAND_ERROR_CONFLICTING_CARRIER_ID 9 Attempted to assign a new carrier with an ID that is already used by other carrier on the same line"},{"location":"protocol-documentation.html#responsecommandstatus","title":"Response.Command.Status","text":"Name Number Description COMMAND_STATUS_UNSPECIFIED 0 This command status is unused, and will never be returned. It is reserved as the default status code according to protobuf specification. COMMAND_STATUS_PROGRESSING 1 Command currently executing. COMMAND_STATUS_COMPLETED 2 Command completed. COMMAND_STATUS_FAILED 3 Command execution failed."},{"location":"protocol-documentation.html#responselinecarrierstatestate","title":"Response.Line.Carrier.State.State","text":"Name Number Description CARRIER_STATE_NONE 0 CARRIER_STATE_CALIBRATING 1 Carrier is currently operating for line calibration. CARRIER_STATE_CALIBRATE_COMPLETED 2 Carrier has completed line calibration, and may now be used for normal operation. CARRIER_STATE_MOVING 3 Carrier is currently moving towards target destination. CARRIER_STATE_MOVE_COMPLETED 4 Carrier has arrived within threshold at target destination. CARRIER_STATE_INITIALIZING 5 Carrier is initializing. Must not be used until initialization is completed. CARRIER_STATE_INITIALIZE_COMPLETED 6 Carrier initialization completed. May now be used for normal operation. CARRIER_STATE_PUSHING 7 Carrier is being pushed by axis. Used to eject carrier from line. CARRIER_STATE_PULLING 9 Carrier is being pulled by axis. Must not be used until pull is completed. CARRIER_STATE_OVERCURRENT 11 Overcurrent detected in carrier axis motor. Carrier movement has been canceled."},{"location":"protocol-documentation.html#scalar-value-types","title":"Scalar Value Types","text":".proto Type Notes C++ Java Python Go C# PHP Ruby double double double float float64 double float Float float float float float float32 float float Float int32 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint32 instead. int32 int int int32 int integer Bignum or Fixnum (as required) int64 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint64 instead. int64 long int/long int64 long integer/string Bignum uint32 Uses variable-length encoding. uint32 int int/long uint32 uint integer Bignum or Fixnum (as required) uint64 Uses variable-length encoding. uint64 long int/long uint64 ulong integer/string Bignum or Fixnum (as required) sint32 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int32s. int32 int int int32 int integer Bignum or Fixnum (as required) sint64 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int64s. int64 long int/long int64 long integer/string Bignum fixed32 Always four bytes. More efficient than uint32 if values are often greater than 2^28. uint32 int int uint32 uint integer Bignum or Fixnum (as required) fixed64 Always eight bytes. More efficient than uint64 if values are often greater than 2^56. uint64 long int/long uint64 ulong integer/string Bignum sfixed32 Always four bytes. int32 int int int32 int integer Bignum or Fixnum (as required) sfixed64 Always eight bytes. int64 long int/long int64 long integer/string Bignum bool bool boolean boolean bool bool boolean TrueClass/FalseClass string A string must always contain UTF-8 encoded or 7-bit ASCII text. string String str/unicode string string string String (UTF-8) bytes May contain any arbitrary sequence of bytes. string ByteString str []byte ByteString string String (ASCII-8BIT)"}]} \ No newline at end of file +var __index = {"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"],"fields":{"title":{"boost":1000.0},"text":{"boost":1.0},"tags":{"boost":1000000.0}}},"docs":[{"location":"index.html","title":"PMF MMC system","text":"

PMF provides the Motion Motor Control (MMC) system for controlling Linear Motor Systems (LMS) with ease and high precision.

"},{"location":"index.html#getting-started","title":"Getting started","text":""},{"location":"index.html#mmc-server","title":"MMC Server","text":"

The MMC Server acts as an endpoint that allows multiple clients to interface with the LMS. The server must run on a PC connected to the first driver of the LMS. Contact our engineers to obtain the MMC Server files and organize them as follows:

mmc-server\n\u251c\u2500 config.json5\n\u251c\u2500 mmc.exe\n\u2514\u2500 mmc.pdb\n
Navigate to the mmc-server folder and run the executable:
mmc.exe --log_level=info\n

"},{"location":"index.html#mmc-api","title":"MMC-API","text":"

Our API is built with Protobuf, offering cross-language compatibility to support your programming language of choice. To integrate our API into your program, ensure your working environment supports Protobuf. For complete integration instructions, see the MMC-API Guidelines page.

"},{"location":"index.html#conventions","title":"Conventions","text":"

This section defines the terminology used throughout the PMF MMC documentation.

"},{"location":"index.html#system-hierarchy","title":"System Hierarchy","text":"

The following terms apply to the PMF MMC system:

"},{"location":"index.html#id-constraints","title":"ID Constraints","text":"

Important: ID Indexing

All system IDs (Lines, Drivers, Axes, and Carriers) use 1-based indexing. The first ID is always 1.

Entity Max ID Calculation / Notes Line 256 Maximum number of lines supported per track. Driver 256 Maximum number of drivers per line. Axis 768 Based on 256 drivers \u00d7 3 axes per driver. Carrier 768 Maximum number of moveable magnets per line."},{"location":"changelog.html","title":"Changelog","text":"

All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

"},{"location":"changelog.html#200-2026-03-16","title":"2.0.0 - 2026-03-16","text":""},{"location":"changelog.html#added","title":"Added","text":""},{"location":"changelog.html#changed","title":"Changed","text":""},{"location":"changelog.html#removed","title":"Removed","text":""},{"location":"changelog.html#fixed","title":"Fixed","text":""},{"location":"changelog.html#121-2026-01-21","title":"1.2.1 - 2026-01-21","text":""},{"location":"mmc-api.html","title":"MMC-API Guidelines","text":"

This page covers how to use MMC-API to operate on LMS connected to PMF's MMC system.

"},{"location":"mmc-api.html#mmc-api-structure","title":"MMC-API Structure","text":"

The MMC API consists of three categories: core, command, and info. Each category contains corresponding requests and responses. Please refer to the protocol documentation page for the expected response for each request.

"},{"location":"mmc-api.html#mmc-core","title":"MMC Core","text":"

Use MMC core messages to retrieve server information and track configuration. PMF recommends that clients verify compatibility with the server API version before operation. Starting from version 2.0.0, breaking changes may occur between major versions, therefore clients must ensure they are compatible with the server's API version. Mismatched versions may result in invalid requests or undefined behavior. Clients must fetch the track configuration prior to operating the PMF MMC system to ensure all messages passed to the server contain valid parameters. Refer to the MMC core documentation for a comprehensive list of message types and expected responses.

"},{"location":"mmc-api.html#mmc-command","title":"MMC Command","text":"

Use MMC command messages to operate the PMF MMC system. Clients must use the following rules when sending MMC command messages.

Monitor command status via the command info request defined in the MMC Info section. A list of commands are available on MMC command documentation.

"},{"location":"mmc-api.html#mmc-info","title":"MMC Info","text":"

Use MMC info messages to monitor the real-time state of the track and command status. The client can specify which track information to request by enabling the relevant flags within the track info message definition. The API also allows filtering track info based on driver range, axis range, or specific carrier IDs. Refer to the MMC info documentation for the complete message definitions used to request track and command states.

"},{"location":"mmc-api.html#create-request","title":"Create Request","text":"

This section demonstrates how to construct and encode a request for transmission. The first example illustrates how to decode and validate a response before use. Subsequent examples will omit the response processing logic to focus on request creation and key considerations for specific commands.

Info

Client must exclusively use the mmc.Request message type to send requests to the server. The server always returns an mmc.Response message to be decoded on client side. Any other message sent to server will return mmc.Response.request_error, showing the message is invalid.

"},{"location":"mmc-api.html#requesting-core-information","title":"Requesting Core Information","text":"

Info

A core request message contains only one enum field. The following example demonstrates how to request the API version used by the server. Other core requests are implemented in the same manner.

Warning

Sending a core request with kind CORE_REQUEST_KIND_SERVER_INFO will always return mmc.Response.core.request_error.

zigpython

Tip

Zig users can directly use the pmotionf/mmc-api repository for ease of integration. If you are using a different Zig version, generate the Zig files from the source Protobuf files using zig-protobuf library.

const api = @import(\"mmc-api\");\n// Create a request and encode the message. Encode with passing the\n// transport writer interface pointer and allocator. Send the message by \n// flush the writer..\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .core = .{ .kind = .CORE_REQUEST_KIND_SERVER_INFO },\n    },\n};\ntry request.encode(&writer.interface, allocator);\ntry writer.interface.flush();\n// Receive and decode the message by passing the reader interface pointer \n// and allocator.\nconst decoded: api.protobuf.mmc.Response = try .decode(\n    &client.reader.interface,\n    client.allocator,\n);\nswitch (decoded.body orelse std.log.err(\"Invalid Response\",.{})) {\n    .core => |core_resp| switch (core_resp.body orelse\n        std.log.err(\"Invalid Response\",.{})) {\n        .server => |server| std.log.info(\n              \"Server API version: {}.{}.{}\",\n              .{server.api.major, server.api.minor, server.api.patch,}\n          ),\n          .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n          else => std.log.err(\"Invalid Response\",.{}),\n    },\n    .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n    else => std.log.err(\"Invalid Response\",.{}),\n};\n
import mmc_pb2 as mmc\n\n# Snipped: Create and connect socket to server\n\n# Create a request message\nrequest = mmc.Request()\nrequest.core.kind = mmc.mmc_dot_core__pb2.Request.CORE_REQUEST_KIND_SERVER_INFO\n\n# Snipped: Send and receive the message\n\n# Parse response\nmsg = mmc.Response()\nmsg.ParseFromString(response)\n\n# Validate and use the response accordingly\nif msg.WhichOneof(\"body\") == \"request_error\":\n    print(\"Error: \", mmc.Request.Error.Name(msg.request_error))\nelif msg.WhichOneof(\"body\") == \"core\":\n    # Validate if the core response that we receive is `api_version`\n    if msg.core.WhichOneof(\"body\") == \"request_error\":\n        print(\n            \"Error: \",\n            mmc.mmc_dot_core__pb2.Request.Error.Name(msg.core.request_error),\n        )\n    elif msg.core.WhichOneof(\"body\") == \"server\":\n        api = msg.core.server.api\n        print(\n            f\"Server API Version: {api.major}.{api.minor}.{api.patch}\"\n      )\n    else:\n        print(\"Invalid Response\")\nelse:\n    print(\"Invalid Response\")\n\ns.close()\n
"},{"location":"mmc-api.html#command-request","title":"Command Request","text":"

Mandatory Command Cleanup

Every command request returns a unique Command ID. The client is required to:

  1. Track the command status using this ID.
  2. Invoke remove_command once the state reaches COMPLETED or FAILED.

Failure to remove finished commands will block the server queue and prevent further command execution.

Check Error Reason

If the command status is FAILED, users can find a descriptive reason by checking the command's error field.

"},{"location":"mmc-api.html#initialize-carrier","title":"Initialize Carrier","text":"

Info

A carrier must be initialized before any actions can be performed. The initialize command is one of many available methods for initializing carriers. This command is sent to the axis specified by the axis parameter.

Unique Carrier ID Requirement

The client must ensure the carrier_id is unique across the entire line. If the ID is already in use by another initialized carrier on the same line, the server will return CONFLICTING_CARRIER_ID.

Example

The following request initializes an uninitialized carrier with ID 1 on the first line in the forward direction. This carrier's position is on top of axis 1 and axis 2.

zigpython
const api = @import(\"mmc-api\");\n\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .initialize = .{\n                    .line = 1,\n                    .axis = 2,\n                    .carrier = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .link_axis = .DIRECTION_FORWARD,\n                },\n            },\n        },\n    },\n};\n// Snipped content: \n// - Send `initialize` command\n// - Receive command ID as the response of command request\n// - Track command state until state `COMPLETED`\n// - Send `remove_command` command\n// - Receive `removed_id` response as the response of `remove_command` request\n
import mmc_pb2 as mmc\n\n# Creating a request message\nCommand = mmc.mmc_dot_command__pb2.Request()\nrequest = mmc.Request()\nrequest.command.initialize.line = 1\nrequest.command.initialize.axis = 2\nrequest.command.initialize.carrier = 1\nrequest.command.initialize.direction = Command.Direction.DIRECTION_FORWARD\nrequest.command.initialize.link_axis = Command.Direction.DIRECTION_BACKWARD\n# Snipped content: \n# - Send `initialize` command\n# - Receive command ID as the response of command request\n# - Track command state until state `COMPLETED`\n# - Send `remove_command` command\n# - Receive `removed_id` response as the response of `remove_command` request\n
"},{"location":"mmc-api.html#auto-initialize-carriers","title":"Auto Initialize Carriers","text":"

Info

Auto initialize all carriers on the specified lines simultaneously. This process operates on carrier clusters, where a cluster is defined as a group of uninitialized carriers located on adjacent axis.

Warning

Each cluster requires at least one free axis to successfully perform the auto-initialization. Any cluster lacking a free axis will be ignored, and all carriers within that cluster will remain uninitialized upon command completion.

Tip

Ignore the acceleration and velocity fields to use the default values. The default value are:

Example

Auto initialize all carriers on line 1 and line 2.

zigpython
const api = @import(\"mmc-api\");\n\n// Allocate lines\nvar lines: std.ArrayList(\n    api.protobuf.mmc.command.Request.AutoInitialize.Line,\n) = .empty;\ndefer lines.deinit(allocator);\n\n// Define first line\ntry lines.append(allocator, .{\n    .line = 1,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Define second line\ntry lines.append(allocator, .{\n    .line = 2,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .auto_initialize = .{\n                    .lines = lines,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n\n# Define first line\nline1 = Command.AutoInitialize.Line()\nline1.line = 1\nline1.velocity = 600\nline1.acceleration = 6000\n\n# Define second line\nline2 = Command.AutoInitialize.Line()\nline2.line = 2\nline2.velocity = 600\nline2.acceleration = 6000\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.auto_initialize.lines.append(line1)\nrequest.command.auto_initialize.lines.append(line2)\n
"},{"location":"mmc-api.html#deinitialize-carriers","title":"Deinitialize Carriers","text":"

Info

Deinitialize will release motor control on the specified carriers and remove carrier states from MMC system. Deinitialize all carriers on a line by not specifying a target. If a target is specified, carriers are deinitialized based on that target:

Example

Deinitialize carrier 1 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .deinitialize = .{\n                    .line = line.id,\n                    .target = .{ .carrier = 1 }\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.deinitialize.line = 1\nrequest.command.deinitialize.carrier = 1\n
"},{"location":"mmc-api.html#move-carrier","title":"Move Carrier","text":"

Tip

Track the carrier state until it reaches MOVE_COMPLETED before sending further commands to the specified carrier to avoid unwanted behavior. The command state COMPLETED only indicates that the command was successfully received and is being processed by the MMC system.

Warning

The target field must be specified by the user, and only the last target value will be serialized to the server. See Oneof for complete a description on Oneof protobuf type.

Example

Move initialized carrier 1 to axis 3 on the second line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .move = .{\n                    .line = 2,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .target = .{.axis = 3},\n                    .control = .CONTROL_POSITION,\n                    .disable_cas = false,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.move.line = 2\nrequest.command.move.carrier = 1\nrequest.command.move.velocity = 1000\nrequest.command.move.acceleration = 6000\nrequest.command.move.axis = 3\n# mmc.Control() message is not generated by protoc compiler because Python does\n# not allow to use definition based on namespace.\n# 1 for CONTROL_POSITION\n# 2 for CONTROL_VELOCITY.\nrequest.command.move.control = 1\nrequest.command.move.disable_cas = False\n
"},{"location":"mmc-api.html#push","title":"Push","text":"

Info

Forcefully moves an initialized carrier on the specified axis by one carrier length. Use this movement to cross a line boundary, which deinitializes the carrier from the current line upon completion.

If the carrier field is provided in the push command, the axis enters a pushing state. In this state, the axis remains busy and waits for the specified carrier to arrive; once it arrives, the axis automatically pushes the carrier.

Warning

When pushing the carrier to a different line, the receiving axis on the destination line must be in a pulling state.

Tip

To disable the pushing state on an axis, utilize the stop push command.

Example

Push carrier on axis 1 of line 2 backward to line 1.

Warning

The destination axis on line 1 must be in pulling state.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .push = .{\n                    .line = 2,\n                    .axis = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.push.line = 2\nrequest.command.push.axis = 1\nrequest.command.push.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.push.velocity = 1000\nrequest.command.push.acceleration = 6000\n
"},{"location":"mmc-api.html#pull","title":"Pull","text":"

Info

Initialize an incoming carrier located outside the current line. This command puts the specified axis into pulling state. This initialization procedure has the following behavior:

Example

Set axis 6 of line 1 to pulling state, and move the pulled carrier to axis 3.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pull = .{\n                    .line = 1,\n                    .axis = 6,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .direction = .DIRECTION_BACKWARD,\n                    .transition = .{\n                        .control = .CONTROL_POSITION,\n                        .disable_cas = false,\n                        .target = .{.axis = 3},\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.pull.line = 1\nrequest.command.pull.axis = 6\nrequest.command.pull.carrier = 1\nrequest.command.pull.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.pull.velocity = 1000\nrequest.command.pull.acceleration = 6000\nrequest.command.pull.transition.control = 1\nrequest.command.pull.transition.disable_cas = False\nrequest.command.pull.transition.axis = 3\n
"},{"location":"mmc-api.html#release-carrier","title":"Release Carrier","text":"

Info

Put the initialized carrier into the NONE state, allowing it to be moved manually or by external systems.

Example

Release control of carrier 1 on line 1.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .release = .{\n                    .line = 1,\n                    .target = .{.carrier = 1},\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.release.line = 1\nrequest.command.release.carrier = 1\n
"},{"location":"mmc-api.html#calibrate-line","title":"Calibrate Line","text":"

Info

To calibrate the drivers' configuration on a line, an uninitialized carrier must be located at the center of the first axis

Example

Calibrate the drivers' configuration on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .calibrate = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.calibrate.line = 1\n
"},{"location":"mmc-api.html#stop-push","title":"Stop Push","text":"

Tip

To reset pushing state on all axis, ignore the axes field.

Example

Reset the pushing state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_push = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_push.line = 1\nrequest.command.stop_push.axes.start = 1\nrequest.command.stop_push.axes.end = 4\n
"},{"location":"mmc-api.html#stop-pull","title":"Stop Pull","text":"

Tip

To reset the pulling state on all axes, omit the axes field.

Example

Reset the pulling state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_pull = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_pull.line = 1\nrequest.command.stop_pull.axes.start = 1\nrequest.command.stop_pull.axes.end = 4\n
"},{"location":"mmc-api.html#set-carrier-id","title":"Set Carrier ID","text":"

Warning

The carrier ID of each carrier must be unique within a line.

Example

Change the carrier ID of carrier 1 to 4 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_carrier_id = .{\n                    .line = 1,\n                    .carrier = 1,\n                    .new_carrier = 4,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_carrier_id.line = 1\nrequest.command.set_carrier_id.carrier = 1\nrequest.command.set_carrier_id.new_carrier = 4\n
"},{"location":"mmc-api.html#set-zero","title":"Set Zero","text":"

Example

Set the zero point of the first line.

Warning

An initialized carrier must be located on the first axis of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_zero = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_zero.line = 1\n
"},{"location":"mmc-api.html#clear-errors","title":"Clear Errors","text":"

Warning

Always clear errors whenever an error is detected on an axis or driver. Failing to clear errors may result in unwanted behavior.

Tip

Ignore the axes field to clear errors on all drivers and axes on the line.

Example

Clear all errors on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .clear_errors = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.clear_errors.line = 1\n
"},{"location":"mmc-api.html#emergency-stop","title":"Emergency Stop","text":"

Tip

Pass an empty list to stop operations on all lines.

Example

Stop operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop.lines.extend([])\n
"},{"location":"mmc-api.html#pause-execution","title":"Pause Execution","text":"

Tip

Pass empty list to pause operations on all lines.

Example

Pause operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pause = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.pause.lines.extend([])\n
"},{"location":"mmc-api.html#resume-execution","title":"Resume Execution","text":"

Tip

Pass an empty list to resume operation on all lines.

Example

Resume operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .@\"resume\" = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.resume.lines.extend([])\n
"},{"location":"mmc-api.html#remove-command","title":"Remove Command","text":"

Warning

Failure to remove a command will block the queue and prevent the server from accepting further commands.

Tip

Always check the command status after sending a command message. (Request Command State)

Example

Remove the command with ID 1 from the server.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .remove_command = .{.command = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Creating a request message\nrequest = mmc.Request()\nrequest.command.remove_command.command = id\n
"},{"location":"mmc-api.html#info-request","title":"Info Request","text":""},{"location":"mmc-api.html#request-command-state","title":"Request Command State","text":"

Example

Wait till the command state becomes COMPLETED or FAILED, then remove the command.

zigpython
const api = @import(\"mmc-api\");\n\nfn waitCommand(id: u32) !void {\n    defer removeCommand(id);\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .command = .{ .id = id },\n                },\n            },\n        },\n    };\n    while (true) {\n        try request.encode(&writer.interface, allocator);\n        try writer.interface.flush();\n        var decoded: api.protobuf.mmc.Response = try .decode(\n            &reader.interface,\n            allocator,\n        );\n        defer decoded.deinit(allocator);\n        const command_response = switch (decoded.body orelse\n            return error.InvalidResponse) {\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n                return;\n            },\n            .info => |info_resp| switch (info_resp.body orelse\n                return error.InvalidResponse) {\n                .command => |commands_resp| commands_resp.items.items[0],\n                .request_error => |req_err| {\n                    std.log.err(\"{t}\", .{req_err});\n                    return;\n                },\n                else => return error.InvalidResponse,\n            },\n            else => return error.InvalidResponse,\n        };\n        switch (command_response.status) {\n            .COMMAND_STATUS_PROGRESSING => {}, // continue the loop\n            .COMMAND_STATUS_COMPLETED => return,\n            .COMMAND_STATUS_FAILED => {\n                std.log.err(\"{t}\", .{command_response.@\"error\".?});\n                return;\n            },\n            .COMMAND_STATUS_UNSPECIFIED => return error.InvalidResponse,\n        }\n    }\n}\n
import mmc_pb2 as mmc\n\ndef waitCommand(id):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.command.id = id\n    while True:\n        # Send and receive response\n        s.sendall(request.SerializeToString())\n        response = s.recv(4096)\n\n        # Parsing the response\n        msg = mmc.Response()\n        msg.ParseFromString(response)\n        Command = mmc.mmc_dot_info__pb2.Response.Command()\n\n        # Validate and use the response accordingly\n        if msg.WhichOneof(\"body\") == \"request_error\":\n            print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n            return\n        elif msg.WhichOneof(\"body\") == \"info\":\n            # Validate if the core response that we receive is `api_version`\n            if msg.info.WhichOneof(\"body\") == \"request_error\":\n                print(\n                    \"Request Error\",\n                    mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n                )\n                return\n            elif msg.info.WhichOneof(\"body\") == \"command\":\n                command = msg.info.command.items[0]\n                if command.status == Command.Status.COMMAND_STATUS_COMPLETED:\n                    removeCommand(id)\n                    return\n                elif command.status == Command.Status.COMMAND_STATUS_FAILED:\n                    removeCommand(id)\n                    raise Exception(Command.Error.Name(command.error))\n                else:\n                    print(\"Invalid Response\")\n                    return\n            else:\n                print(\"Invalid Response\")\n                return\n        else:\n            print(\"Invalid Response\")\n            return\n
"},{"location":"mmc-api.html#request-track-state","title":"Request Track State","text":"

Tip

Certain commands require the client to monitor carrier status to ensure movement is completed.

Warning

Monitor the error flags of driver, axis and carriers to prevent damage to the motor or driver board. Pay close attention to inverter_overheat on the driver and overcurrent flags on the axis; immediately deinitialize any carrier on the affected axes and drivers if these are detected. The overvoltage and undervoltage flags indicate that the system voltage supply may have a problem; please consult with our engineers to resolve the issue.

Request carrier state

Tip

zigpython
const api = @import(\"mmc-api\");\nfn carrierState(line: u32, carrier: u32) !void {\n    var carrier_id = [1]u32{carrier};\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .track = .{\n                        .line = line,\n                        .info_carrier_state = true,\n                        .filter = .{\n                            .carriers = .{\n                                .ids = .fromOwnedSlice(&carrier_id),\n                            },\n                        },\n                    },\n                },\n            },\n        },\n    };\n    try request.encode(&writer.interface, allocator);\n    try writer.interface.flush();\n    var decoded: api.protobuf.mmc.Response = try .decode(\n        &reader.interface,\n        allocator,\n    );\n    defer decoded.deinit(allocator);\n    switch (decoded.body orelse return error.InvalidResponse) {\n        .info => |info_resp| switch (info_resp.body orelse\n            return error.InvalidResponse) {\n            .track => |track_resp| {\n                std.log.info(\"{}\", .{track_resp.carrier_state.items[0]});\n            },\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n            },\n            else => return error.InvalidResponse,\n        },\n        .request_error => |req_err| {\n            std.log.err(\"{t}\", .{req_err});\n            return;\n        },\n        else => return error.InvalidResponse,\n    }\n}\n
import mmc_pb2 as mmc\ndef carrierState(line, carrier):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.track.line = line\n    request.info.track.info_carrier_state = True\n    request.info.track.carriers.ids.append(carrier)\n\n    # Parsing the response\n    msg = mmc.Response()\n    msg.ParseFromString(response)\n    # Validate and use the response accordingly\n    if msg.WhichOneof(\"body\") == \"request_error\":\n        print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n    elif msg.WhichOneof(\"body\") == \"info\":\n        # Validate if the core response that we receive is `api_version`\n        if msg.info.WhichOneof(\"body\") == \"request_error\":\n            print(\n                \"Request Error\",\n                mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n            )\n        elif msg.info.WhichOneof(\"body\") == \"track\":\n            assert len(msg.info.track.carrier_state) != 0\n            carrier = msg.info.track.carrier_state[0]\n            print(carrier)\n        else:\n            print(\"Invalid Response\")\n    else:\n        print(\"Invalid Response\")\n
"},{"location":"protocol-documentation.html","title":"Protocol Documentation","text":""},{"location":"protocol-documentation.html#table-of-contents","title":"Table of Contents","text":"

Top

"},{"location":"protocol-documentation.html#mmcproto","title":"mmc.proto","text":""},{"location":"protocol-documentation.html#request","title":"Request","text":"

Request message. All client-to-server messages should be of this message type.

Field Type Label Description core core.Request Core request. Used to retrieve information about the server or the configured track. command command.Request Command request. Used to send and manage commands to the server, which will execute commands on the connected track. info info.Request Info request. Used to retrieve information about track state or commands processed by the server.

"},{"location":"protocol-documentation.html#response","title":"Response","text":"

Response message. All server-to-client messages will be of this message type.

Field Type Label Description core core.Response Core response. command command.Response Command response. info info.Response Info Response. request_error Request.Error Top-level request error. This error field will be returned only if the top-level request could not be handled properly. Otherwise, response kinds may contain more specific error codes.

"},{"location":"protocol-documentation.html#requesterror","title":"Request.Error","text":"Name Number Description MMC_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. MMC_REQUEST_ERROR_INVALID_MESSAGE 1 The request could not be decoded as a valid protobuf message.

Top

"},{"location":"protocol-documentation.html#rangeproto","title":"range.proto","text":""},{"location":"protocol-documentation.html#range","title":"Range","text":"Field Type Label Description start uint32 Start of range, inclusive. end uint32 End of range, inclusive.

Top

"},{"location":"protocol-documentation.html#mmccommandproto","title":"mmc/command.proto","text":""},{"location":"protocol-documentation.html#request_1","title":"Request","text":"

Command API: List of commands to operate the PMF's motion system.

When a command is sent to the server, it will be queued for execution. Command execution status can be polled through the Info API. The status remains stored in a limited history buffer, and should be cleared with remove_command after completion.

Field Type Label Description calibrate Request.Calibrate Calibrate a line. This command only needs to be run once after hardware setup; calibrated values will remain stored in drivers even after a power cycle. set_zero Request.SetZero Set the zero position of the specified line. This command can be run optionally after calibration, upon which all drivers will store the set zero position of the line. The set zero position will remain unchanged even after a power cycle. initialize Request.Initialize Initialize a carrier. Carriers must be initialized before they can be moved. Initialization is required after every power cycle. auto_initialize Request.AutoInitialize Initialize all carriers of the specified line(s). If no lines are specified, initialize all carriers across all lines in the track. deinitialize Request.Deinitialize Deinitialize a carrier. This removes all carrier information, such as recognized position and carrier ID. move Request.Move Move an initialized carrier to the desired position. pull Request.Pull Pull and initialize a new carrier into a line. push Request.Push Push an initialized carrier to the specified direction. stop_pull Request.StopPull Stop waiting to pull a new carrier at an axis. stop_push Request.StopPush Stop waiting to push an initialized carrier at an axis. release Request.Release Release the motor control of a carrier. clear_errors Request.ClearErrors Clear all errors within the specified driver range. remove_command Request.RemoveCommand Cancel a running command or remove its status history. stop Request.Stop Activate emergency stop for all drivers in line(s). Emergency stop will cause all carriers to decelerate to rest, then reset all carriers' movement commands. pause Request.Pause Activate pause for all drivers in line(s). Pause will cause all carriers to decelerate to rest. On resume, the carriers will continue their previously assigned movement commands. resume Request.Resume Deactivate emergency stop and pause for all drivers in line(s). set_carrier_id Request.SetCarrierId Change an existing carrier ID to a new unique carrier ID.

"},{"location":"protocol-documentation.html#requestautoinitialize","title":"Request.AutoInitialize","text":"

Automatically initialize carriers on every specified lines.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines Request.AutoInitialize.Line repeated

"},{"location":"protocol-documentation.html#requestautoinitializeline","title":"Request.AutoInitialize.Line","text":"Field Type Label Description line uint32 Line ID. velocity float optional Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s (default 600 mm/s). acceleration float optional Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2 (default 6000 mm/s^2)."},{"location":"protocol-documentation.html#requestcalibrate","title":"Request.Calibrate","text":"

Calibrate a line by positioning an uninitialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requestclearerrors","title":"Request.ClearErrors","text":"

Clear all error information on the driver. If a target is specified, clear error information of drivers included in that target. If not, clear error information on all drivers of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. drivers Range Driver ID range. axes Range Axis ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestdeinitialize","title":"Request.Deinitialize","text":"

Clear carrier information located on the axis. If a target is specified, clear information of carriers included in that target. If not, clear all carrier information of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range Axis ID range. drivers Range Driver ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestinitialize","title":"Request.Initialize","text":"

Initialize a carrier.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the new carrier. direction Request.Direction Initialization direction for the new carrier. link_axis Request.Direction optional Linked axis direction from the specified axis.

"},{"location":"protocol-documentation.html#requestmove","title":"Request.Move","text":"

Move a carrier to the desired position.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. axis uint32 Move carrier to the center of the axis. location float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. distance float Move carrier to relative distance to current carrier position. Negative distance moves the carrier backwards. control mmc.Control Control method for moving carrier. disable_cas bool Disable the carrier's collision avoidance system (CAS).

"},{"location":"protocol-documentation.html#requestpause","title":"Request.Pause","text":"

Pause any operation in PMF LMS. Any queued commands in the server will be continued once the resume command is given.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, pause operations only on the specified lines.

"},{"location":"protocol-documentation.html#requestpull","title":"Request.Pull","text":"

Pull and initialize a new carrier into a line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the incoming carrier. direction Request.Direction The direction from which the incoming carrier is moving. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. When the transition location target is set to NaN, the velocity must be 0. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. When the transition location target is set to NaN, the acceleration must be 0. transition Request.Pull.Transition optional Smoothly transition to carrier movement after pull completion.

"},{"location":"protocol-documentation.html#requestpulltransition","title":"Request.Pull.Transition","text":"Field Type Label Description control mmc.Control Control method for moving carrier. disable_cas bool Disabling the carrier's collision avoidance system (CAS). target float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. Pass NaN to pull carrier without motor control, allowing carrier to be pulled with external force."},{"location":"protocol-documentation.html#requestpush","title":"Request.Push","text":"

Push an initialized carrier to the specified direction.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. direction Request.Direction Direction of carrier movement. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. carrier uint32 optional Carrier ID. If provided, wait for the specified carrier at the axis and push it once the carrier arrives.

"},{"location":"protocol-documentation.html#requestrelease","title":"Request.Release","text":"

Release the control imposed by the motor to the carrier. If a target is specified, all motors included in that target release control. Otherwise, all carriers on the provided line will be released from control.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. axes Range Axis ID range. drivers Range Driver ID range.

"},{"location":"protocol-documentation.html#requestremovecommand","title":"Request.RemoveCommand","text":"

Remove a command on the server if the command ID is specified. If no command ID is specified, remove any commands received by the server. If the commands are still progressing, cancel the command execution.

Expected response: mmc.Response.body.command.body.removed_id (uint32).

Field Type Label Description command uint32 optional Command ID.

"},{"location":"protocol-documentation.html#requestresume","title":"Request.Resume","text":"

Resume lines that have been stopped or paused. If the line is not paused or emergency stopped, this command will succeed without any effect.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, resume operations only to those specified lines.

"},{"location":"protocol-documentation.html#requestsetcarrierid","title":"Request.SetCarrierId","text":"

Change the carrier ID of an existing initialized carrier. If the new carrier ID already exists on the line, returns INVALID_CARRIER.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Target existing initialized carrier ID. new_carrier uint32 New desired carrier ID (unique in line).

"},{"location":"protocol-documentation.html#requestsetzero","title":"Request.SetZero","text":"

Set a zero position of a line by positioning an initialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requeststop","title":"Request.Stop","text":"

Send an emergency stop command to stop any operation in PMF LMS. This command also removes all queued commands in the server.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, stop operations only on the specified lines and remove all commands that targeting those lines.

"},{"location":"protocol-documentation.html#requeststoppull","title":"Request.StopPull","text":"

Stop pulling a carrier to the specified axis. If no axis is provided, then all pending carrier pulls on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#requeststoppush","title":"Request.StopPush","text":"

Stop pushing a carrier from the specified axis. If no axis is provided, then all pending carrier pushes on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#response_1","title":"Response","text":"

Response description to the command API.

Field Type Label Description id uint32 Assigned ID for newly sent command. removed_id uint32 ID of cleared existing command. request_error Request.Error Error during command's execution.

"},{"location":"protocol-documentation.html#requestdirection","title":"Request.Direction","text":"Name Number Description DIRECTION_UNSPECIFIED 0 DIRECTION_BACKWARD 1 DIRECTION_FORWARD 2"},{"location":"protocol-documentation.html#requesterror_1","title":"Request.Error","text":"Name Number Description COMMAND_REQUEST_ERROR_UNSPECIFIED 0 COMMAND_REQUEST_ERROR_INVALID_LINE 1 Attempted to use line ID outside of the configured lines. COMMAND_REQUEST_ERROR_INVALID_AXIS 2 Attempted to use axis ID outside of the configured axes of the line. COMMAND_REQUEST_ERROR_INVALID_DRIVER 3 Attempted to use driver ID outside of the configured drivers of the line. COMMAND_REQUEST_ERROR_INVALID_ACCELERATION 4 Attempted to use acceleration value outside of 1-245. COMMAND_REQUEST_ERROR_INVALID_VELOCITY 5 Attempted to use velocity value outside of 1-60. COMMAND_REQUEST_ERROR_INVALID_DIRECTION 6 Using invalid direction for the command. COMMAND_REQUEST_ERROR_INVALID_LOCATION 7 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_DISTANCE 8 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_CARRIER 9 Attempted to send a command to carrier outside of 1-2048. COMMAND_REQUEST_ERROR_MISSING_PARAMETER 10 A command missing the required parameter. COMMAND_REQUEST_ERROR_COMMAND_NOT_FOUND 11 Attempted to remove or cancel a non-existing command. COMMAND_REQUEST_ERROR_CARRIER_NOT_FOUND 12 Attempted to send command to an uninitialized carrier. COMMAND_REQUEST_ERROR_OUT_OF_MEMORY 14 Server unable to receive new command caused by out of memory. Try Command.Request.remove_command to free the memory. COMMAND_REQUEST_ERROR_MAXIMUM_AUTO_INITIALIZE_EXCEEDED 15 Attempted to run more than 8 auto initialize instance. COMMAND_REQUEST_ERROR_CONFLICTING_CARRIER_ID 16 Attempted to assign a carrier ID that is already used by another carrier on the same line. COMMAND_REQUEST_ERROR_INVALID_COMMAND 17 Command index is out of bounds for the configured command status buffer.

Top

"},{"location":"protocol-documentation.html#mmccontrolproto","title":"mmc/control.proto","text":""},{"location":"protocol-documentation.html#control","title":"Control","text":"

Carrier motor control kind.

Name Number Description CONTROL_UNSPECIFIED 0 CONTROL_POSITION 1 Carrier controlled with position priority. CONTROL_VELOCITY 2 Carrier controlled with velocity priority.

Top

"},{"location":"protocol-documentation.html#mmccoreproto","title":"mmc/core.proto","text":""},{"location":"protocol-documentation.html#request_2","title":"Request","text":"Field Type Label Description kind Request.Kind"},{"location":"protocol-documentation.html#response_2","title":"Response","text":"

Response description to the core API.

Field Type Label Description server Response.Server Server process information. track_config Response.TrackConfig Track configuration. request_error Request.Error Error response if the core request could not be handled.

"},{"location":"protocol-documentation.html#responsesemanticversion","title":"Response.SemanticVersion","text":"Field Type Label Description major uint32 minor uint32 patch uint32"},{"location":"protocol-documentation.html#responseserver","title":"Response.Server","text":"

Server version and name.

Field Type Label Description name string Server name. version Response.SemanticVersion Server implementation version. api Response.SemanticVersion

"},{"location":"protocol-documentation.html#responsetrackconfig","title":"Response.TrackConfig","text":"Field Type Label Description lines Response.TrackConfig.Line repeated All configured lines in track."},{"location":"protocol-documentation.html#responsetrackconfigline","title":"Response.TrackConfig.Line","text":"Field Type Label Description id uint32 Line ID. Numeric ID, starting from 1, that is unique to each line in the track. This ID is used to address the line in other requests. name string Configured line name. This name is otherwise unused by the API, and is provided to the client for end-user convenience. axes uint32 Total number of axes in the line. axis_length float Length of each axis in the line, in millimeters. carrier_length float Carrier dimension parallel to carrier movement, in millimeters. drivers uint32 Total number of drivers in the line. carrier_width float Carrier dimension perpendicular to carrier movement, in millimeters."},{"location":"protocol-documentation.html#requesterror_2","title":"Request.Error","text":"Name Number Description CORE_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. CORE_REQUEST_ERROR_REQUEST_UNKNOWN 1 The core request kind was unspecified."},{"location":"protocol-documentation.html#requestkind","title":"Request.Kind","text":"Name Number Description CORE_REQUEST_KIND_UNSPECIFIED 0 This request kind is unused, and should never be sent. It is reserved as the default request kind according to protobuf specification. CORE_REQUEST_KIND_SERVER_INFO 2 Request server process information. This includes the configured server name and server implementation version. CORE_REQUEST_KIND_TRACK_CONFIG 3 Request the configured track information of the server.

Top

"},{"location":"protocol-documentation.html#mmcinfoproto","title":"mmc/info.proto","text":""},{"location":"protocol-documentation.html#request_3","title":"Request","text":"Field Type Label Description command Request.Command Command information request. Get current status of command; necessary to determine if command is currently running, completed, or failed. track Request.Track Track information request. Get current track state information."},{"location":"protocol-documentation.html#requestcommand","title":"Request.Command","text":"

Request for status of specified command ID from the server. If no command ID is provided, then request for status of all commands from the server.

Expected response: mmc.Response.body.info.body.commands

Field Type Label Description id uint32 optional

"},{"location":"protocol-documentation.html#requesttrack","title":"Request.Track","text":"

Request track state information from server. One or more of the info_ flags must be enabled to select the kind of track information desired. A filter may be optionally provided to limit the source of information from the track.

Expected response: mmc.Response.body.info.body.track

Field Type Label Description lines uint32 repeated Line ID(s). Select line(s) from which information will be retrieved. info_driver_state bool Retrieve driver state information. info_driver_errors bool Retrieve driver error information. info_axis_state bool Retrieve axis state information. info_axis_errors bool Retrieve axis errors information. info_carrier_state bool Retrieve carrier state information. drivers Range Retrieve information from driver ID range. Driver information flags will include drivers within this range. Axis information flags will include every axis belonging to the drivers in this range. Carrier information flags will include every carrier currently controlled by one of the drivers in this range. axes Range Retrieve information from axis ID range. Driver information flags will include drivers that contain one of the axes within this range. Axis information flags will include axes within this range. Carrier information flags will include every carrier currently controlled by one of the axes in this range. carriers Request.Track.Ids Retrieve information from carrier IDs. Driver information flags will include drivers that control one of the carriers within this list. Axis information flags will include axes that control one of the carriers within this list. Carrier information flags will include carriers within this list.

"},{"location":"protocol-documentation.html#requesttrackids","title":"Request.Track.Ids","text":"

List of IDs. At least one ID must be provided.

Field Type Label Description ids uint32 repeated

"},{"location":"protocol-documentation.html#response_3","title":"Response","text":"Field Type Label Description command Response.Commands Information for requested command(s). If empty, no matching command(s) was found. track Response.Track Information for requested track state. request_error Request.Error Info request error. This error field will be returned if the provided info request could not be handled properly."},{"location":"protocol-documentation.html#responsecommand","title":"Response.Command","text":"Field Type Label Description id uint32 Command ID. Valid IDs begin from 1, and may be reused after command status is cleared from server history. status Response.Command.Status Command status. error Response.Command.Error optional Command error response, only if the status is COMMAND_STATUS_FAILED."},{"location":"protocol-documentation.html#responsecommands","title":"Response.Commands","text":"Field Type Label Description items Response.Command repeated"},{"location":"protocol-documentation.html#responseline","title":"Response.Line","text":"Field Type Label Description id uint32 Line ID. driver_state Response.Line.Driver.State repeated Driver state information list. Empty if request flag was disabled. driver_errors Response.Line.Driver.Error repeated Driver error information list. Empty if request flag was disabled. axis_state Response.Line.Axis.State repeated Axis state information list. Empty if request flag was disabled. axis_errors Response.Line.Axis.Error repeated Axis error information list. Empty if request flag was disabled. carrier_state Response.Line.Carrier.State repeated Carrier state information list. Empty if request flag was disabled."},{"location":"protocol-documentation.html#responselineaxis","title":"Response.Line.Axis","text":""},{"location":"protocol-documentation.html#responselineaxiserror","title":"Response.Line.Axis.Error","text":"Field Type Label Description id uint32 Axis ID. overcurrent bool Motor overcurrent detected. Motor control released to prevent damage."},{"location":"protocol-documentation.html#responselineaxisstate","title":"Response.Line.Axis.State","text":"Field Type Label Description id uint32 Axis ID. motor_active bool Axis is currently controlling a carrier. waiting_pull bool Axis is waiting to pull carrier. waiting_push bool Axis is waiting to push carrier. carrier uint32 Carrier ID; non-zero if an initialized carrier is on the axis. hall_alarm_back bool Axis back hall alarm is active. Magnet is detected above back hall sensor. hall_alarm_front bool Axis front hall alarm is active. Magnet is detected above front hall sensor."},{"location":"protocol-documentation.html#responselinecarrier","title":"Response.Line.Carrier","text":""},{"location":"protocol-documentation.html#responselinecarrierstate","title":"Response.Line.Carrier.State","text":"Field Type Label Description id uint32 Carrier ID. Will always be non-zero. position float Position of the carrier in line, in meters. axis_main uint32 Carrier's primary axis ID. axis_auxiliary uint32 optional Carrier's auxiliary axis ID, if carrier is on top of two axes. cas_disabled bool Collision avoidance system (CAS) disabled. cas_triggered bool Collision avoidance system (CAS) triggered. Carrier will automatically resume movement when path is clear. state Response.Line.Carrier.State.State Carrier state."},{"location":"protocol-documentation.html#responselinedriver","title":"Response.Line.Driver","text":""},{"location":"protocol-documentation.html#responselinedrivererror","title":"Response.Line.Driver.Error","text":"Field Type Label Description id uint32 Driver ID. control_loop_time_exceeded bool Control loop exceeded maximum loop time. inverter_overheat bool Inverter is overheated. undervoltage bool Driver voltage supply too low. overvoltage bool Driver voltage supply too high. comm_error_prev bool Communication error with previous driver in line. comm_error_next bool Communication error with next driver in line."},{"location":"protocol-documentation.html#responselinedriverstate","title":"Response.Line.Driver.State","text":"Field Type Label Description id uint32 Driver ID. connected bool Connection status between driver and server. busy bool Driver is currently executing a command. motor_disabled bool Driver motor release activated. All driver motors are inactive. stopped bool Driver emergency stop activated. paused bool Driver pause activated."},{"location":"protocol-documentation.html#responsetrack","title":"Response.Track","text":"Field Type Label Description lines Response.Line repeated"},{"location":"protocol-documentation.html#requesterror_3","title":"Request.Error","text":"Name Number Description INFO_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. INFO_REQUEST_ERROR_INVALID_LINE 1 Invalid line ID provided. Ensure that line ID exists in track configuration. INFO_REQUEST_ERROR_INVALID_AXIS 2 Invalid axis ID provided. Ensure that axis ID exists in line. INFO_REQUEST_ERROR_INVALID_DRIVER 3 Invalid driver ID provided. Ensure that driver ID exists in line. INFO_REQUEST_ERROR_MISSING_PARAMETER 4 Request is missing a required parameter. Ensure that at least one of the information flag is selected when requesting track information. INFO_REQUEST_ERROR_COMMAND_NOT_FOUND 5 Attempted to request information from a non-existing command. INFO_REQUEST_ERROR_INVALID_COMMAND 6 Command index is out of bounds for the configured command status buffer. INFO_REQUEST_ERROR_INVALID_CARRIER 7 Attempted to send a command to carrier outside of range."},{"location":"protocol-documentation.html#responsecommanderror","title":"Response.Command.Error","text":"Name Number Description COMMAND_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. COMMAND_ERROR_INVALID_SYSTEM_STATE 1 System state prevented successful command execution. Ensure that all preconditions are met with track info request before sending command. COMMAND_ERROR_INVALID_CARRIER_ID 2 Deprecated. Check COMMAND_REQUEST_ERROR_INVALID_CARRIER on Command.Request.Error. COMMAND_ERROR_DRIVER_DISCONNECTED 3 Driver connection failed while command progressing. COMMAND_ERROR_UNEXPECTED 4 Unexpected command execution error. This is likely an implementation bug; please contact PMF support for assistance. COMMAND_ERROR_CARRIER_NOT_FOUND 5 Target carrier is removed while command progressing. COMMAND_ERROR_CARRIER_ALREADY_INITIALIZED 6 Attempted to initialize an initialized carrier. COMMAND_ERROR_DRIVER_STOPPED 7 Target driver is stopped while command progressing. Consider resume the driver before sending further command. COMMAND_ERROR_INVALID_CARRIER_TARGET 8 Carrier targeting a location outside of the configured track. COMMAND_ERROR_CONFLICTING_CARRIER_ID 9 Attempted to assign a new carrier with an ID that is already used by other carrier on the same line"},{"location":"protocol-documentation.html#responsecommandstatus","title":"Response.Command.Status","text":"Name Number Description COMMAND_STATUS_UNSPECIFIED 0 This command status is unused, and will never be returned. It is reserved as the default status code according to protobuf specification. COMMAND_STATUS_PROGRESSING 1 Command currently executing. COMMAND_STATUS_COMPLETED 2 Command completed. COMMAND_STATUS_FAILED 3 Command execution failed."},{"location":"protocol-documentation.html#responselinecarrierstatestate","title":"Response.Line.Carrier.State.State","text":"Name Number Description CARRIER_STATE_NONE 0 CARRIER_STATE_CALIBRATING 1 Carrier is currently operating for line calibration. CARRIER_STATE_CALIBRATE_COMPLETED 2 Carrier has completed line calibration, and may now be used for normal operation. CARRIER_STATE_MOVING 3 Carrier is currently moving towards target destination. CARRIER_STATE_MOVE_COMPLETED 4 Carrier has arrived within threshold at target destination. CARRIER_STATE_INITIALIZING 5 Carrier is initializing. Must not be used until initialization is completed. CARRIER_STATE_INITIALIZE_COMPLETED 6 Carrier initialization completed. May now be used for normal operation. CARRIER_STATE_PUSHING 7 Carrier is being pushed by axis. Used to eject carrier from line. CARRIER_STATE_PULLING 9 Carrier is being pulled by axis. Must not be used until pull is completed. CARRIER_STATE_OVERCURRENT 11 Overcurrent detected in carrier axis motor. Carrier movement has been canceled."},{"location":"protocol-documentation.html#scalar-value-types","title":"Scalar Value Types","text":".proto Type Notes C++ Java Python Go C# PHP Ruby double double double float float64 double float Float float float float float float32 float float Float int32 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint32 instead. int32 int int int32 int integer Bignum or Fixnum (as required) int64 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint64 instead. int64 long int/long int64 long integer/string Bignum uint32 Uses variable-length encoding. uint32 int int/long uint32 uint integer Bignum or Fixnum (as required) uint64 Uses variable-length encoding. uint64 long int/long uint64 ulong integer/string Bignum or Fixnum (as required) sint32 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int32s. int32 int int int32 int integer Bignum or Fixnum (as required) sint64 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int64s. int64 long int/long int64 long integer/string Bignum fixed32 Always four bytes. More efficient than uint32 if values are often greater than 2^28. uint32 int int uint32 uint integer Bignum or Fixnum (as required) fixed64 Always eight bytes. More efficient than uint64 if values are often greater than 2^56. uint64 long int/long uint64 ulong integer/string Bignum sfixed32 Always four bytes. int32 int int int32 int integer Bignum or Fixnum (as required) sfixed64 Always eight bytes. int64 long int/long int64 long integer/string Bignum bool bool boolean boolean bool bool boolean TrueClass/FalseClass string A string must always contain UTF-8 encoded or 7-bit ASCII text. string String str/unicode string string string String (UTF-8) bytes May contain any arbitrary sequence of bytes. string ByteString str []byte ByteString string String (ASCII-8BIT)"}]} \ No newline at end of file diff --git a/site/search/search_index.json b/site/search/search_index.json index 20f61a0..d9938e5 100644 --- a/site/search/search_index.json +++ b/site/search/search_index.json @@ -1 +1 @@ -{"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"],"fields":{"title":{"boost":1000.0},"text":{"boost":1.0},"tags":{"boost":1000000.0}}},"docs":[{"location":"index.html","title":"PMF MMC system","text":"

PMF provides the Motion Motor Control (MMC) system for controlling Linear Motor Systems (LMS) with ease and high precision.

"},{"location":"index.html#getting-started","title":"Getting started","text":""},{"location":"index.html#mmc-server","title":"MMC Server","text":"

The MMC Server acts as an endpoint that allows multiple clients to interface with the LMS. The server must run on a PC connected to the first driver of the LMS. Contact our engineers to obtain the MMC Server files and organize them as follows:

mmc-server\n\u251c\u2500 config.json5\n\u251c\u2500 mmc.exe\n\u2514\u2500 mmc.pdb\n
Navigate to the mmc-server folder and run the executable:
mmc.exe --log_level=info\n

"},{"location":"index.html#mmc-api","title":"MMC-API","text":"

Our API is built with Protobuf, offering cross-language compatibility to support your programming language of choice. To integrate our API into your program, ensure your working environment supports Protobuf. For complete integration instructions, see the MMC-API Guidelines page.

"},{"location":"index.html#conventions","title":"Conventions","text":"

This section defines the terminology used throughout the PMF MMC documentation.

"},{"location":"index.html#system-hierarchy","title":"System Hierarchy","text":"

The following terms apply to the PMF MMC system:

"},{"location":"index.html#id-constraints","title":"ID Constraints","text":"

Important: ID Indexing

All system IDs (Lines, Drivers, Axes, and Carriers) use 1-based indexing. The first ID is always 1.

Entity Max ID Calculation / Notes Line 256 Maximum number of lines supported per track. Driver 256 Maximum number of drivers per line. Axis 768 Based on 256 drivers \u00d7 3 axes per driver. Carrier 768 Maximum number of moveable magnets per line."},{"location":"changelog.html","title":"Changelog","text":"

All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

"},{"location":"changelog.html#200-2026-03-16","title":"2.0.0 - 2026-03-16","text":""},{"location":"changelog.html#added","title":"Added","text":""},{"location":"changelog.html#changed","title":"Changed","text":""},{"location":"changelog.html#removed","title":"Removed","text":""},{"location":"changelog.html#fixed","title":"Fixed","text":""},{"location":"changelog.html#121-2026-01-21","title":"1.2.1 - 2026-01-21","text":""},{"location":"mmc-api.html","title":"MMC-API Guidelines","text":"

This page covers how to use MMC-API to operate on LMS connected to PMF's MMC system.

"},{"location":"mmc-api.html#mmc-api-structure","title":"MMC-API Structure","text":"

The MMC API consists of three categories: core, command, and info. Each category contains corresponding requests and responses. Please refer to the protocol documentation page for the expected response for each request.

"},{"location":"mmc-api.html#mmc-core","title":"MMC Core","text":"

Use MMC core messages to retrieve server information and track configuration. PMF recommends that clients verify compatibility with the server API version before operation. Starting from version 2.0.0, breaking changes may occur between major versions, therefore clients must ensure they are compatible with the server's API version. Mismatched versions may result in invalid requests or undefined behavior. Clients must fetch the track configuration prior to operating the PMF MMC system to ensure all messages passed to the server contain valid parameters. Refer to the MMC core documentation for a comprehensive list of message types and expected responses.

"},{"location":"mmc-api.html#mmc-command","title":"MMC Command","text":"

Use MMC command messages to operate the PMF MMC system. Clients must use the following rules when sending MMC command messages.

Monitor command status via the command info request defined in the MMC Info section. A list of commands are available on MMC command documentation.

"},{"location":"mmc-api.html#mmc-info","title":"MMC Info","text":"

Use MMC info messages to monitor the real-time state of the track and command status. The client can specify which track information to request by enabling the relevant flags within the track info message definition. The API also allows filtering track info based on driver range, axis range, or specific carrier IDs. Refer to the MMC info documentation for the complete message definitions used to request track and command states.

"},{"location":"mmc-api.html#create-request","title":"Create Request","text":"

This section demonstrates how to construct and encode a request for transmission. The first example illustrates how to decode and validate a response before use. Subsequent examples will omit the response processing logic to focus on request creation and key considerations for specific commands.

Info

Client must exclusively use the mmc.Request message type to send requests to the server. The server always returns an mmc.Response message to be decoded on client side. Any other message sent to server will return mmc.Response.request_error, showing the message is invalid.

"},{"location":"mmc-api.html#requesting-core-information","title":"Requesting Core Information","text":"

Info

A core request message contains only one enum field. The following example demonstrates how to request the API version used by the server. Other core requests are implemented in the same manner.

Warning

Sending a core request with kind CORE_REQUEST_KIND_SERVER_INFO will always return mmc.Response.core.request_error.

zigpython

Tip

Zig users can directly use the pmotionf/mmc-api repository for ease of integration. If you are using a different Zig version, generate the Zig files from the source Protobuf files using zig-protobuf library.

const api = @import(\"mmc-api\");\n// Create a request and encode the message. Encode with passing the\n// transport writer interface pointer and allocator. Send the message by \n// flush the writer..\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .core = .{ .kind = .CORE_REQUEST_KIND_SERVER_INFO },\n    },\n};\ntry request.encode(&writer.interface, allocator);\ntry writer.interface.flush();\n// Receive and decode the message by passing the reader interface pointer \n// and allocator.\nconst decoded: api.protobuf.mmc.Response = try .decode(\n    &client.reader.interface,\n    client.allocator,\n);\nswitch (decoded.body orelse std.log.err(\"Invalid Response\",.{})) {\n    .core => |core_resp| switch (core_resp.body orelse\n        std.log.err(\"Invalid Response\",.{})) {\n        .server => |server| std.log.info(\n              \"Server API version: {}.{}.{}\",\n              .{server.api.major, server.api.minor, server.api.patch,}\n          ),\n          .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n          else => std.log.err(\"Invalid Response\",.{}),\n    },\n    .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n    else => std.log.err(\"Invalid Response\",.{}),\n};\n
import mmc_pb2 as mmc\n\n# Snipped: Create and connect socket to server\n\n# Create a request message\nrequest = mmc.Request()\nrequest.core.kind = mmc.mmc_dot_core__pb2.Request.CORE_REQUEST_KIND_SERVER_INFO\n\n# Snipped: Send and receive the message\n\n# Parse response\nmsg = mmc.Response()\nmsg.ParseFromString(response)\n\n# Validate and use the response accordingly\nif msg.WhichOneof(\"body\") == \"request_error\":\n    print(\"Error: \", mmc.Request.Error.Name(msg.request_error))\nelif msg.WhichOneof(\"body\") == \"core\":\n    # Validate if the core response that we receive is `api_version`\n    if msg.core.WhichOneof(\"body\") == \"request_error\":\n        print(\n            \"Error: \",\n            mmc.mmc_dot_core__pb2.Request.Error.Name(msg.core.request_error),\n        )\n    elif msg.core.WhichOneof(\"body\") == \"server\":\n        api = msg.core.server.api\n        print(\n            f\"Server API Version: {api.major}.{api.minor}.{api.patch}\"\n      )\n    else:\n        print(\"Invalid Response\")\nelse:\n    print(\"Invalid Response\")\n\ns.close()\n
"},{"location":"mmc-api.html#command-request","title":"Command Request","text":"

Mandatory Command Cleanup

Every command request returns a unique Command ID. The client is required to:

  1. Track the command status using this ID.
  2. Invoke remove_command once the state reaches COMPLETED or FAILED.

Failure to remove finished commands will block the server queue and prevent further command execution.

Check Error Reason

If the command status is FAILED, users can find a descriptive reason by checking the command's error field.

"},{"location":"mmc-api.html#initialize-carrier","title":"Initialize Carrier","text":"

Info

A carrier must be initialized before any actions can be performed. The initialize command is one of many available methods for initializing carriers. This command is sent to the axis specified by the axis parameter.

Unique Carrier ID Requirement

The client must ensure the carrier_id is unique across the entire line. If the ID is already in use by another initialized carrier on the same line, the server will return CONFLICTING_CARRIER_ID.

Example

The following request initializes an uninitialized carrier with ID 1 on the first line in the forward direction. This carrier's position is on top of axis 1 and axis 2.

zigpython
const api = @import(\"mmc-api\");\n\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .initialize = .{\n                    .line = 1,\n                    .axis = 2,\n                    .carrier = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .link_axis = .DIRECTION_FORWARD,\n                },\n            },\n        },\n    },\n};\n// Snipped content: \n// - Send `initialize` command\n// - Receive command ID as the response of command request\n// - Track command state until state `COMPLETED`\n// - Send `remove_command` command\n// - Receive `removed_id` response as the response of `remove_command` request\n
import mmc_pb2 as mmc\n\n# Creating a request message\nCommand = mmc.mmc_dot_command__pb2.Request()\nrequest = mmc.Request()\nrequest.command.initialize.line = 1\nrequest.command.initialize.axis = 2\nrequest.command.initialize.carrier = 1\nrequest.command.initialize.direction = Command.Direction.DIRECTION_FORWARD\nrequest.command.initialize.link_axis = Command.Direction.DIRECTION_BACKWARD\n# Snipped content: \n# - Send `initialize` command\n# - Receive command ID as the response of command request\n# - Track command state until state `COMPLETED`\n# - Send `remove_command` command\n# - Receive `removed_id` response as the response of `remove_command` request\n
"},{"location":"mmc-api.html#auto-initialize-carriers","title":"Auto Initialize Carriers","text":"

Info

Auto initialize all carriers on the specified lines simultaneously. This process operates on carrier clusters, where a cluster is defined as a group of uninitialized carriers located on adjacent axis.

Warning

Each cluster requires at least one free axis to successfully perform the auto-initialization. Any cluster lacking a free axis will be ignored, and all carriers within that cluster will remain uninitialized upon command completion.

Tip

Ignore the acceleration and velocity fields to use the default values. The default value are:

Example

Auto initialize all carriers on line 1 and line 2.

zigpython
const api = @import(\"mmc-api\");\n\n// Allocate lines\nvar lines: std.ArrayList(\n    api.protobuf.mmc.command.Request.AutoInitialize.Line,\n) = .empty;\ndefer lines.deinit(allocator);\n\n// Define first line\ntry lines.append(allocator, .{\n    .line = 1,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Define second line\ntry lines.append(allocator, .{\n    .line = 2,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .auto_initialize = .{\n                    .lines = lines,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n\n# Define first line\nline1 = Command.AutoInitialize.Line()\nline1.line = 1\nline1.velocity = 600\nline1.acceleration = 6000\n\n# Define second line\nline2 = Command.AutoInitialize.Line()\nline2.line = 2\nline2.velocity = 600\nline2.acceleration = 6000\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.auto_initialize.lines.append(line1)\nrequest.command.auto_initialize.lines.append(line2)\n
"},{"location":"mmc-api.html#deinitialize-carriers","title":"Deinitialize Carriers","text":"

Info

Deinitialize will release motor control on the specified carriers and remove carrier states from MMC system. Deinitialize all carriers on a line by not specifying a target. If a target is specified, carriers are deinitialized based on that target:

Example

Deinitialize carrier 1 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .deinitialize = .{\n                    .line = line.id,\n                    .target = .{ .carrier = 1 }\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.deinitialize.line = 1\nrequest.command.deinitialize.carrier = 1\n
"},{"location":"mmc-api.html#move-carrier","title":"Move Carrier","text":"

Tip

Track the carrier state until it reaches MOVE_COMPLETED before sending further commands to the specified carrier to avoid unwanted behavior. The command state COMPLETED only indicates that the command was successfully received and is being processed by the MMC system.

Warning

The target field must be specified by the user, and only the last target value will be serialized to the server. See Oneof for complete a description on Oneof protobuf type.

Example

Move initialized carrier 1 to axis 3 on the second line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .move = .{\n                    .line = 2,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .target = .{.axis = 3},\n                    .control = .CONTROL_POSITION,\n                    .disable_cas = false,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.move.line = 2\nrequest.command.move.carrier = 1\nrequest.command.move.velocity = 1000\nrequest.command.move.acceleration = 6000\nrequest.command.move.axis = 3\n# mmc.Control() message is not generated by protoc compiler because Python does\n# not allow to use definition based on namespace.\n# 1 for CONTROL_POSITION\n# 2 for CONTROL_VELOCITY.\nrequest.command.move.control = 1\nrequest.command.move.disable_cas = False\n
"},{"location":"mmc-api.html#push","title":"Push","text":"

Info

Forcefully moves an initialized carrier on the specified axis by one carrier length. Use this movement to cross a line boundary, which deinitializes the carrier from the current line upon completion.

If the carrier field is provided in the push command, the axis enters a pushing state. In this state, the axis remains busy and waits for the specified carrier to arrive; once it arrives, the axis automatically pushes the carrier.

Warning

When pushing the carrier to a different line, the receiving axis on the destination line must be in a pulling state.

Tip

To disable the pushing state on an axis, utilize the stop push command.

Example

Push carrier on axis 1 of line 2 backward to line 1.

Warning

The destination axis on line 1 must be in pulling state.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .push = .{\n                    .line = 2,\n                    .axis = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.push.line = 2\nrequest.command.push.axis = 1\nrequest.command.push.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.push.velocity = 1000\nrequest.command.push.acceleration = 6000\n
"},{"location":"mmc-api.html#pull","title":"Pull","text":"

Info

Initialize an incoming carrier located outside the current line. This command puts the specified axis into pulling state. This initialization procedure has the following behavior:

Example

Set axis 6 of line 1 to pulling state, and move the pulled carrier to axis 3.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pull = .{\n                    .line = 1,\n                    .axis = 6,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .direction = .DIRECTION_BACKWARD,\n                    .transition = .{\n                        .control = .CONTROL_POSITION,\n                        .disable_cas = false,\n                        .target = .{.axis = 3},\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.pull.line = 1\nrequest.command.pull.axis = 6\nrequest.command.pull.carrier = 1\nrequest.command.pull.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.pull.velocity = 1000\nrequest.command.pull.acceleration = 6000\nrequest.command.pull.transition.control = 1\nrequest.command.pull.transition.disable_cas = False\nrequest.command.pull.transition.axis = 3\n
"},{"location":"mmc-api.html#release-carrier","title":"Release Carrier","text":"

Info

Put the initialized carrier into the NONE state, allowing it to be moved manually or by external systems.

Example

Release control of carrier 1 on line 1.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .release = .{\n                    .line = 1,\n                    .target = .{.carrier = 1},\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.release.line = 1\nrequest.command.release.carrier = 1\n
"},{"location":"mmc-api.html#calibrate-line","title":"Calibrate Line","text":"

Info

To calibrate the drivers' configuration on a line, an uninitialized carrier must be located at the center of the first axis

Example

Calibrate the drivers' configuration on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .calibrate = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.calibrate.line = 1\n
"},{"location":"mmc-api.html#stop-push","title":"Stop Push","text":"

Tip

To reset pushing state on all axis, ignore the axes field.

Example

Reset the pushing state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_push = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_push.line = 1\nrequest.command.stop_push.axes.start = 1\nrequest.command.stop_push.axes.end = 4\n
"},{"location":"mmc-api.html#stop-pull","title":"Stop Pull","text":"

Tip

To reset the pulling state on all axes, omit the axes field.

Example

Reset the pulling state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_pull = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_pull.line = 1\nrequest.command.stop_pull.axes.start = 1\nrequest.command.stop_pull.axes.end = 4\n
"},{"location":"mmc-api.html#set-carrier-id","title":"Set Carrier ID","text":"

Warning

The carrier ID of each carrier must be unique within a line.

Example

Change the carrier ID of carrier 1 to 4 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_carrier_id = .{\n                    .line = 1,\n                    .carrier = 1,\n                    .new_carrier = 4,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_carrier_id.line = 1\nrequest.command.set_carrier_id.carrier = 1\nrequest.command.set_carrier_id.new_carrier = 4\n
"},{"location":"mmc-api.html#set-zero","title":"Set Zero","text":"

Example

Set the zero point of the first line.

Warning

An initialized carrier must be located on the first axis of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_zero = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_zero.line = 1\n
"},{"location":"mmc-api.html#clear-errors","title":"Clear Errors","text":"

Warning

Always clear errors whenever an error is detected on an axis or driver. Failing to clear errors may result in unwanted behavior.

Tip

Ignore the axes field to clear errors on all drivers and axes on the line.

Example

Clear all errors on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .clear_errors = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.clear_errors.line = 1\n
"},{"location":"mmc-api.html#emergency-stop","title":"Emergency Stop","text":"

Tip

Pass an empty list to stop operations on all lines.

Example

Stop operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop.lines.extend([])\n
"},{"location":"mmc-api.html#pause-execution","title":"Pause Execution","text":"

Tip

Pass empty list to pause operations on all lines.

Example

Pause operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pause = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.pause.lines.extend([])\n
"},{"location":"mmc-api.html#resume-execution","title":"Resume Execution","text":"

Tip

Pass an empty list to resume operation on all lines.

Example

Resume operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .@\"resume\" = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.resume.lines.extend([])\n
"},{"location":"mmc-api.html#remove-command","title":"Remove Command","text":"

Warning

Failure to remove a command will block the queue and prevent the server from accepting further commands.

Tip

Always check the command status after sending a command message. (Request Command State)

Example

Remove the command with ID 1 from the server.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .remove_command = .{.command = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Creating a request message\nrequest = mmc.Request()\nrequest.command.remove_command.command = id\n
"},{"location":"mmc-api.html#info-request","title":"Info Request","text":""},{"location":"mmc-api.html#request-command-state","title":"Request Command State","text":"

Example

Wait till the command state becomes COMPLETED or FAILED, then remove the command.

zigpython
const api = @import(\"mmc-api\");\n\nfn waitCommand(id: u32) !void {\n    defer removeCommand(id);\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .command = .{ .id = id },\n                },\n            },\n        },\n    };\n    while (true) {\n        try request.encode(&writer.interface, allocator);\n        try writer.interface.flush();\n        var decoded: api.protobuf.mmc.Response = try .decode(\n            &reader.interface,\n            allocator,\n        );\n        defer decoded.deinit(allocator);\n        const command_response = switch (decoded.body orelse\n            return error.InvalidResponse) {\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n                return;\n            },\n            .info => |info_resp| switch (info_resp.body orelse\n                return error.InvalidResponse) {\n                .command => |commands_resp| commands_resp.items.items[0],\n                .request_error => |req_err| {\n                    std.log.err(\"{t}\", .{req_err});\n                    return;\n                },\n                else => return error.InvalidResponse,\n            },\n            else => return error.InvalidResponse,\n        };\n        switch (command_response.status) {\n            .COMMAND_STATUS_PROGRESSING => {}, // continue the loop\n            .COMMAND_STATUS_COMPLETED => return,\n            .COMMAND_STATUS_FAILED => {\n                std.log.err(\"{t}\", .{command_response.@\"error\".?});\n                return;\n            },\n            .COMMAND_STATUS_UNSPECIFIED => return error.InvalidResponse,\n        }\n    }\n}\n
import mmc_pb2 as mmc\n\ndef waitCommand(id):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.command.id = id\n    while True:\n        # Send and receive response\n        s.sendall(request.SerializeToString())\n        response = s.recv(4096)\n\n        # Parsing the response\n        msg = mmc.Response()\n        msg.ParseFromString(response)\n        Command = mmc.mmc_dot_info__pb2.Response.Command()\n\n        # Validate and use the response accordingly\n        if msg.WhichOneof(\"body\") == \"request_error\":\n            print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n            return\n        elif msg.WhichOneof(\"body\") == \"info\":\n            # Validate if the core response that we receive is `api_version`\n            if msg.info.WhichOneof(\"body\") == \"request_error\":\n                print(\n                    \"Request Error\",\n                    mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n                )\n                return\n            elif msg.info.WhichOneof(\"body\") == \"command\":\n                command = msg.info.command.items[0]\n                if command.status == Command.Status.COMMAND_STATUS_COMPLETED:\n                    removeCommand(id)\n                    return\n                elif command.status == Command.Status.COMMAND_STATUS_FAILED:\n                    removeCommand(id)\n                    raise Exception(Command.Error.Name(command.error))\n                else:\n                    print(\"Invalid Response\")\n                    return\n            else:\n                print(\"Invalid Response\")\n                return\n        else:\n            print(\"Invalid Response\")\n            return\n
"},{"location":"mmc-api.html#request-track-state","title":"Request Track State","text":"

Tip

Certain commands require the client to monitor carrier status to ensure movement is completed.

Warning

Monitor the error flags of driver, axis and carriers to prevent damage to the motor or driver board. Pay close attention to inverter_overheat on the driver and overcurrent flags on the axis; immediately deinitialize any carrier on the affected axes and drivers if these are detected. The overvoltage and undervoltage flags indicate that the system voltage supply may have a problem; please consult with our engineers to resolve the issue.

Request carrier state

Tip

zigpython
const api = @import(\"mmc-api\");\nfn carrierState(line: u32, carrier: u32) !void {\n    var carrier_id = [1]u32{carrier};\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .track = .{\n                        .line = line,\n                        .info_carrier_state = true,\n                        .filter = .{\n                            .carriers = .{\n                                .ids = .fromOwnedSlice(&carrier_id),\n                            },\n                        },\n                    },\n                },\n            },\n        },\n    };\n    try request.encode(&writer.interface, allocator);\n    try writer.interface.flush();\n    var decoded: api.protobuf.mmc.Response = try .decode(\n        &reader.interface,\n        allocator,\n    );\n    defer decoded.deinit(allocator);\n    switch (decoded.body orelse return error.InvalidResponse) {\n        .info => |info_resp| switch (info_resp.body orelse\n            return error.InvalidResponse) {\n            .track => |track_resp| {\n                std.log.info(\"{}\", .{track_resp.carrier_state.items[0]});\n            },\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n            },\n            else => return error.InvalidResponse,\n        },\n        .request_error => |req_err| {\n            std.log.err(\"{t}\", .{req_err});\n            return;\n        },\n        else => return error.InvalidResponse,\n    }\n}\n
import mmc_pb2 as mmc\ndef carrierState(line, carrier):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.track.line = line\n    request.info.track.info_carrier_state = True\n    request.info.track.carriers.ids.append(carrier)\n\n    # Parsing the response\n    msg = mmc.Response()\n    msg.ParseFromString(response)\n    # Validate and use the response accordingly\n    if msg.WhichOneof(\"body\") == \"request_error\":\n        print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n    elif msg.WhichOneof(\"body\") == \"info\":\n        # Validate if the core response that we receive is `api_version`\n        if msg.info.WhichOneof(\"body\") == \"request_error\":\n            print(\n                \"Request Error\",\n                mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n            )\n        elif msg.info.WhichOneof(\"body\") == \"track\":\n            assert len(msg.info.track.carrier_state) != 0\n            carrier = msg.info.track.carrier_state[0]\n            print(carrier)\n        else:\n            print(\"Invalid Response\")\n    else:\n        print(\"Invalid Response\")\n
"},{"location":"protocol-documentation.html","title":"Protocol Documentation","text":""},{"location":"protocol-documentation.html#table-of-contents","title":"Table of Contents","text":"

Top

"},{"location":"protocol-documentation.html#mmcproto","title":"mmc.proto","text":""},{"location":"protocol-documentation.html#request","title":"Request","text":"

Request message. All client-to-server messages should be of this message type.

Field Type Label Description core core.Request Core request. Used to retrieve information about the server or the configured track. command command.Request Command request. Used to send and manage commands to the server, which will execute commands on the connected track. info info.Request Info request. Used to retrieve information about track state or commands processed by the server.

"},{"location":"protocol-documentation.html#response","title":"Response","text":"

Response message. All server-to-client messages will be of this message type.

Field Type Label Description core core.Response Core response. command command.Response Command response. info info.Response Info Response. request_error Request.Error Top-level request error. This error field will be returned only if the top-level request could not be handled properly. Otherwise, response kinds may contain more specific error codes.

"},{"location":"protocol-documentation.html#requesterror","title":"Request.Error","text":"Name Number Description MMC_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. MMC_REQUEST_ERROR_INVALID_MESSAGE 1 The request could not be decoded as a valid protobuf message.

Top

"},{"location":"protocol-documentation.html#rangeproto","title":"range.proto","text":""},{"location":"protocol-documentation.html#range","title":"Range","text":"Field Type Label Description start uint32 Start of range, inclusive. end uint32 End of range, inclusive.

Top

"},{"location":"protocol-documentation.html#mmccommandproto","title":"mmc/command.proto","text":""},{"location":"protocol-documentation.html#request_1","title":"Request","text":"

Command API: List of commands to operate the PMF's motion system.

When a command is sent to the server, it will be queued for execution. Command execution status can be polled through the Info API. The status remains stored in a limited history buffer, and should be cleared with remove_command after completion.

Field Type Label Description calibrate Request.Calibrate Calibrate a line. This command only needs to be run once after hardware setup; calibrated values will remain stored in drivers even after a power cycle. set_zero Request.SetZero Set the zero position of the specified line. This command can be run optionally after calibration, upon which all drivers will store the set zero position of the line. The set zero position will remain unchanged even after a power cycle. initialize Request.Initialize Initialize a carrier. Carriers must be initialized before they can be moved. Initialization is required after every power cycle. auto_initialize Request.AutoInitialize Initialize all carriers of the specified line(s). If no lines are specified, initialize all carriers across all lines in the track. deinitialize Request.Deinitialize Deinitialize a carrier. This removes all carrier information, such as recognized position and carrier ID. move Request.Move Move an initialized carrier to the desired position. pull Request.Pull Pull and initialize a new carrier into a line. push Request.Push Push an initialized carrier to the specified direction. stop_pull Request.StopPull Stop waiting to pull a new carrier at an axis. stop_push Request.StopPush Stop waiting to push an initialized carrier at an axis. release Request.Release Release the motor control of a carrier. clear_errors Request.ClearErrors Clear all errors within the specified driver range. remove_command Request.RemoveCommand Cancel a running command or remove its status history. stop Request.Stop Activate emergency stop for all drivers in line(s). Emergency stop will cause all carriers to decelerate to rest, then reset all carriers' movement commands. pause Request.Pause Activate pause for all drivers in line(s). Pause will cause all carriers to decelerate to rest. On resume, the carriers will continue their previously assigned movement commands. resume Request.Resume Deactivate emergency stop and pause for all drivers in line(s). set_carrier_id Request.SetCarrierId Change an existing carrier ID to a new unique carrier ID.

"},{"location":"protocol-documentation.html#requestautoinitialize","title":"Request.AutoInitialize","text":"

Automatically initialize carriers on every specified lines.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines Request.AutoInitialize.Line repeated

"},{"location":"protocol-documentation.html#requestautoinitializeline","title":"Request.AutoInitialize.Line","text":"Field Type Label Description line uint32 Line ID. velocity float optional Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s (default 600 mm/s). acceleration float optional Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2 (default 6000 mm/s^2)."},{"location":"protocol-documentation.html#requestcalibrate","title":"Request.Calibrate","text":"

Calibrate a line by positioning an uninitialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requestclearerrors","title":"Request.ClearErrors","text":"

Clear all error information on the driver. If a target is specified, clear error information of drivers included in that target. If not, clear error information on all drivers of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. drivers Range Driver ID range. axes Range Axis ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestdeinitialize","title":"Request.Deinitialize","text":"

Clear carrier information located on the axis. If a target is specified, clear information of carriers included in that target. If not, clear all carrier information of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range Axis ID range. drivers Range Driver ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestinitialize","title":"Request.Initialize","text":"

Initialize a carrier.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the new carrier. direction Request.Direction Initialization direction for the new carrier. link_axis Request.Direction optional Linked axis direction from the specified axis.

"},{"location":"protocol-documentation.html#requestmove","title":"Request.Move","text":"

Move a carrier to the desired position.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. axis uint32 Move carrier to the center of the axis. location float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. distance float Move carrier to relative distance to current carrier position. Negative distance moves the carrier backwards. control mmc.Control Control method for moving carrier. disable_cas bool Disable the carrier's collision avoidance system (CAS).

"},{"location":"protocol-documentation.html#requestpause","title":"Request.Pause","text":"

Pause any operation in PMF LMS. Any queued commands in the server will be continued once the resume command is given.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, pause operations only on the specified lines.

"},{"location":"protocol-documentation.html#requestpull","title":"Request.Pull","text":"

Pull and initialize a new carrier into a line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the incoming carrier. direction Request.Direction The direction from which the incoming carrier is moving. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. When the transition location target is set to NaN, the velocity must be 0. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. When the transition location target is set to NaN, the acceleration must be 0. transition Request.Pull.Transition optional Smoothly transition to carrier movement after pull completion.

"},{"location":"protocol-documentation.html#requestpulltransition","title":"Request.Pull.Transition","text":"Field Type Label Description control mmc.Control Control method for moving carrier. disable_cas bool Disabling the carrier's collision avoidance system (CAS). target float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. Pass NaN to pull carrier without motor control, allowing carrier to be pulled with external force."},{"location":"protocol-documentation.html#requestpush","title":"Request.Push","text":"

Push an initialized carrier to the specified direction.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. direction Request.Direction Direction of carrier movement. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. carrier uint32 optional Carrier ID. If provided, wait for the specified carrier at the axis and push it once the carrier arrives.

"},{"location":"protocol-documentation.html#requestrelease","title":"Request.Release","text":"

Release the control imposed by the motor to the carrier. If a target is specified, all motors included in that target release control. Otherwise, all carriers on the provided line will be released from control.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. axes Range Axis ID range. drivers Range Driver ID range.

"},{"location":"protocol-documentation.html#requestremovecommand","title":"Request.RemoveCommand","text":"

Remove a command on the server if the command ID is specified. If no command ID is specified, remove any commands received by the server. If the commands are still progressing, cancel the command execution.

Expected response: mmc.Response.body.command.body.removed_id (uint32).

Field Type Label Description command uint32 optional Command ID.

"},{"location":"protocol-documentation.html#requestresume","title":"Request.Resume","text":"

Resume lines that have been stopped or paused. If the line is not paused or emergency stopped, this command will succeed without any effect.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, resume operations only to those specified lines.

"},{"location":"protocol-documentation.html#requestsetcarrierid","title":"Request.SetCarrierId","text":"

Change the carrier ID of an existing initialized carrier. If the new carrier ID already exists on the line, returns INVALID_CARRIER.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Target existing initialized carrier ID. new_carrier uint32 New desired carrier ID (unique in line).

"},{"location":"protocol-documentation.html#requestsetzero","title":"Request.SetZero","text":"

Set a zero position of a line by positioning an initialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requeststop","title":"Request.Stop","text":"

Send an emergency stop command to stop any operation in PMF LMS. This command also removes all queued commands in the server.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, stop operations only on the specified lines and remove all commands that targeting those lines.

"},{"location":"protocol-documentation.html#requeststoppull","title":"Request.StopPull","text":"

Stop pulling a carrier to the specified axis. If no axis is provided, then all pending carrier pulls on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#requeststoppush","title":"Request.StopPush","text":"

Stop pushing a carrier from the specified axis. If no axis is provided, then all pending carrier pushes on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#response_1","title":"Response","text":"

Response description to the command API.

Field Type Label Description id uint32 Assigned ID for newly sent command. removed_id uint32 ID of cleared existing command. request_error Request.Error Error during command's execution.

"},{"location":"protocol-documentation.html#requestdirection","title":"Request.Direction","text":"Name Number Description DIRECTION_UNSPECIFIED 0 DIRECTION_BACKWARD 1 DIRECTION_FORWARD 2"},{"location":"protocol-documentation.html#requesterror_1","title":"Request.Error","text":"Name Number Description COMMAND_REQUEST_ERROR_UNSPECIFIED 0 COMMAND_REQUEST_ERROR_INVALID_LINE 1 Attempted to use line ID outside of the configured lines. COMMAND_REQUEST_ERROR_INVALID_AXIS 2 Attempted to use axis ID outside of the configured axes of the line. COMMAND_REQUEST_ERROR_INVALID_DRIVER 3 Attempted to use driver ID outside of the configured drivers of the line. COMMAND_REQUEST_ERROR_INVALID_ACCELERATION 4 Attempted to use acceleration value outside of 1-245. COMMAND_REQUEST_ERROR_INVALID_VELOCITY 5 Attempted to use velocity value outside of 1-60. COMMAND_REQUEST_ERROR_INVALID_DIRECTION 6 Using invalid direction for the command. COMMAND_REQUEST_ERROR_INVALID_LOCATION 7 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_DISTANCE 8 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_CARRIER 9 Attempted to send a command to carrier outside of 1-2048. COMMAND_REQUEST_ERROR_MISSING_PARAMETER 10 A command missing the required parameter. COMMAND_REQUEST_ERROR_COMMAND_NOT_FOUND 11 Attempted to remove or cancel a non-existing command. COMMAND_REQUEST_ERROR_CARRIER_NOT_FOUND 12 Attempted to send command to an uninitialized carrier. COMMAND_REQUEST_ERROR_OUT_OF_MEMORY 14 Server unable to receive new command caused by out of memory. Try Command.Request.remove_command to free the memory. COMMAND_REQUEST_ERROR_MAXIMUM_AUTO_INITIALIZE_EXCEEDED 15 Attempted to run more than 8 auto initialize instance. COMMAND_REQUEST_ERROR_CONFLICTING_CARRIER_ID 16 Attempted to assign a carrier ID that is already used by another carrier on the same line. COMMAND_REQUEST_ERROR_INVALID_COMMAND 17 Command index is out of bounds for the configured command status buffer.

Top

"},{"location":"protocol-documentation.html#mmccontrolproto","title":"mmc/control.proto","text":""},{"location":"protocol-documentation.html#control","title":"Control","text":"

Carrier motor control kind.

Name Number Description CONTROL_UNSPECIFIED 0 CONTROL_POSITION 1 Carrier controlled with position priority. CONTROL_VELOCITY 2 Carrier controlled with velocity priority.

Top

"},{"location":"protocol-documentation.html#mmccoreproto","title":"mmc/core.proto","text":""},{"location":"protocol-documentation.html#request_2","title":"Request","text":"Field Type Label Description kind Request.Kind"},{"location":"protocol-documentation.html#response_2","title":"Response","text":"

Response description to the core API.

Field Type Label Description server Response.Server Server process information. track_config Response.TrackConfig Track configuration. request_error Request.Error Error response if the core request could not be handled.

"},{"location":"protocol-documentation.html#responsesemanticversion","title":"Response.SemanticVersion","text":"Field Type Label Description major uint32 minor uint32 patch uint32"},{"location":"protocol-documentation.html#responseserver","title":"Response.Server","text":"

Server version and name.

Field Type Label Description name string Server name. version Response.SemanticVersion Server implementation version. api Response.SemanticVersion

"},{"location":"protocol-documentation.html#responsetrackconfig","title":"Response.TrackConfig","text":"Field Type Label Description lines Response.TrackConfig.Line repeated All configured lines in track."},{"location":"protocol-documentation.html#responsetrackconfigline","title":"Response.TrackConfig.Line","text":"Field Type Label Description id uint32 Line ID. Numeric ID, starting from 1, that is unique to each line in the track. This ID is used to address the line in other requests. name string Configured line name. This name is otherwise unused by the API, and is provided to the client for end-user convenience. axes uint32 Total number of axes in the line. axis_length float Length of each axis in the line, in meters. carrier_length float Carrier magnet length, in meters. drivers uint32 Total number of drivers in the line."},{"location":"protocol-documentation.html#requesterror_2","title":"Request.Error","text":"Name Number Description CORE_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. CORE_REQUEST_ERROR_REQUEST_UNKNOWN 1 The core request kind was unspecified."},{"location":"protocol-documentation.html#requestkind","title":"Request.Kind","text":"Name Number Description CORE_REQUEST_KIND_UNSPECIFIED 0 This request kind is unused, and should never be sent. It is reserved as the default request kind according to protobuf specification. CORE_REQUEST_KIND_SERVER_INFO 2 Request server process information. This includes the configured server name and server implementation version. CORE_REQUEST_KIND_TRACK_CONFIG 3 Request the configured track information of the server.

Top

"},{"location":"protocol-documentation.html#mmcinfoproto","title":"mmc/info.proto","text":""},{"location":"protocol-documentation.html#request_3","title":"Request","text":"Field Type Label Description command Request.Command Command information request. Get current status of command; necessary to determine if command is currently running, completed, or failed. track Request.Track Track information request. Get current track state information."},{"location":"protocol-documentation.html#requestcommand","title":"Request.Command","text":"

Request for status of specified command ID from the server. If no command ID is provided, then request for status of all commands from the server.

Expected response: mmc.Response.body.info.body.commands

Field Type Label Description id uint32 optional

"},{"location":"protocol-documentation.html#requesttrack","title":"Request.Track","text":"

Request track state information from server. One or more of the info_ flags must be enabled to select the kind of track information desired. A filter may be optionally provided to limit the source of information from the track.

Expected response: mmc.Response.body.info.body.track

Field Type Label Description lines uint32 repeated Line ID(s). Select line(s) from which information will be retrieved. info_driver_state bool Retrieve driver state information. info_driver_errors bool Retrieve driver error information. info_axis_state bool Retrieve axis state information. info_axis_errors bool Retrieve axis errors information. info_carrier_state bool Retrieve carrier state information. drivers Range Retrieve information from driver ID range. Driver information flags will include drivers within this range. Axis information flags will include every axis belonging to the drivers in this range. Carrier information flags will include every carrier currently controlled by one of the drivers in this range. axes Range Retrieve information from axis ID range. Driver information flags will include drivers that contain one of the axes within this range. Axis information flags will include axes within this range. Carrier information flags will include every carrier currently controlled by one of the axes in this range. carriers Request.Track.Ids Retrieve information from carrier IDs. Driver information flags will include drivers that control one of the carriers within this list. Axis information flags will include axes that control one of the carriers within this list. Carrier information flags will include carriers within this list.

"},{"location":"protocol-documentation.html#requesttrackids","title":"Request.Track.Ids","text":"

List of IDs. At least one ID must be provided.

Field Type Label Description ids uint32 repeated

"},{"location":"protocol-documentation.html#response_3","title":"Response","text":"Field Type Label Description command Response.Commands Information for requested command(s). If empty, no matching command(s) was found. track Response.Track Information for requested track state. request_error Request.Error Info request error. This error field will be returned if the provided info request could not be handled properly."},{"location":"protocol-documentation.html#responsecommand","title":"Response.Command","text":"Field Type Label Description id uint32 Command ID. Valid IDs begin from 1, and may be reused after command status is cleared from server history. status Response.Command.Status Command status. error Response.Command.Error optional Command error response, only if the status is COMMAND_STATUS_FAILED."},{"location":"protocol-documentation.html#responsecommands","title":"Response.Commands","text":"Field Type Label Description items Response.Command repeated"},{"location":"protocol-documentation.html#responseline","title":"Response.Line","text":"Field Type Label Description id uint32 Line ID. driver_state Response.Line.Driver.State repeated Driver state information list. Empty if request flag was disabled. driver_errors Response.Line.Driver.Error repeated Driver error information list. Empty if request flag was disabled. axis_state Response.Line.Axis.State repeated Axis state information list. Empty if request flag was disabled. axis_errors Response.Line.Axis.Error repeated Axis error information list. Empty if request flag was disabled. carrier_state Response.Line.Carrier.State repeated Carrier state information list. Empty if request flag was disabled."},{"location":"protocol-documentation.html#responselineaxis","title":"Response.Line.Axis","text":""},{"location":"protocol-documentation.html#responselineaxiserror","title":"Response.Line.Axis.Error","text":"Field Type Label Description id uint32 Axis ID. overcurrent bool Motor overcurrent detected. Motor control released to prevent damage."},{"location":"protocol-documentation.html#responselineaxisstate","title":"Response.Line.Axis.State","text":"Field Type Label Description id uint32 Axis ID. motor_active bool Axis is currently controlling a carrier. waiting_pull bool Axis is waiting to pull carrier. waiting_push bool Axis is waiting to push carrier. carrier uint32 Carrier ID; non-zero if an initialized carrier is on the axis. hall_alarm_back bool Axis back hall alarm is active. Magnet is detected above back hall sensor. hall_alarm_front bool Axis front hall alarm is active. Magnet is detected above front hall sensor."},{"location":"protocol-documentation.html#responselinecarrier","title":"Response.Line.Carrier","text":""},{"location":"protocol-documentation.html#responselinecarrierstate","title":"Response.Line.Carrier.State","text":"Field Type Label Description id uint32 Carrier ID. Will always be non-zero. position float Position of the carrier in line, in meters. axis_main uint32 Carrier's primary axis ID. axis_auxiliary uint32 optional Carrier's auxiliary axis ID, if carrier is on top of two axes. cas_disabled bool Collision avoidance system (CAS) disabled. cas_triggered bool Collision avoidance system (CAS) triggered. Carrier will automatically resume movement when path is clear. state Response.Line.Carrier.State.State Carrier state."},{"location":"protocol-documentation.html#responselinedriver","title":"Response.Line.Driver","text":""},{"location":"protocol-documentation.html#responselinedrivererror","title":"Response.Line.Driver.Error","text":"Field Type Label Description id uint32 Driver ID. control_loop_time_exceeded bool Control loop exceeded maximum loop time. inverter_overheat bool Inverter is overheated. undervoltage bool Driver voltage supply too low. overvoltage bool Driver voltage supply too high. comm_error_prev bool Communication error with previous driver in line. comm_error_next bool Communication error with next driver in line."},{"location":"protocol-documentation.html#responselinedriverstate","title":"Response.Line.Driver.State","text":"Field Type Label Description id uint32 Driver ID. connected bool Connection status between driver and server. busy bool Driver is currently executing a command. motor_disabled bool Driver motor release activated. All driver motors are inactive. stopped bool Driver emergency stop activated. paused bool Driver pause activated."},{"location":"protocol-documentation.html#responsetrack","title":"Response.Track","text":"Field Type Label Description lines Response.Line repeated"},{"location":"protocol-documentation.html#requesterror_3","title":"Request.Error","text":"Name Number Description INFO_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. INFO_REQUEST_ERROR_INVALID_LINE 1 Invalid line ID provided. Ensure that line ID exists in track configuration. INFO_REQUEST_ERROR_INVALID_AXIS 2 Invalid axis ID provided. Ensure that axis ID exists in line. INFO_REQUEST_ERROR_INVALID_DRIVER 3 Invalid driver ID provided. Ensure that driver ID exists in line. INFO_REQUEST_ERROR_MISSING_PARAMETER 4 Request is missing a required parameter. Ensure that at least one of the information flag is selected when requesting track information. INFO_REQUEST_ERROR_COMMAND_NOT_FOUND 5 Attempted to request information from a non-existing command. INFO_REQUEST_ERROR_INVALID_COMMAND 6 Command index is out of bounds for the configured command status buffer. INFO_REQUEST_ERROR_INVALID_CARRIER 7 Attempted to send a command to carrier outside of range."},{"location":"protocol-documentation.html#responsecommanderror","title":"Response.Command.Error","text":"Name Number Description COMMAND_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. COMMAND_ERROR_INVALID_SYSTEM_STATE 1 System state prevented successful command execution. Ensure that all preconditions are met with track info request before sending command. COMMAND_ERROR_INVALID_CARRIER_ID 2 Deprecated. Check COMMAND_REQUEST_ERROR_INVALID_CARRIER on Command.Request.Error. COMMAND_ERROR_DRIVER_DISCONNECTED 3 Driver connection failed while command progressing. COMMAND_ERROR_UNEXPECTED 4 Unexpected command execution error. This is likely an implementation bug; please contact PMF support for assistance. COMMAND_ERROR_CARRIER_NOT_FOUND 5 Target carrier is removed while command progressing. COMMAND_ERROR_CARRIER_ALREADY_INITIALIZED 6 Attempted to initialize an initialized carrier. COMMAND_ERROR_DRIVER_STOPPED 7 Target driver is stopped while command progressing. Consider resume the driver before sending further command. COMMAND_ERROR_INVALID_CARRIER_TARGET 8 Carrier targeting a location outside of the configured track. COMMAND_ERROR_CONFLICTING_CARRIER_ID 9 Attempted to assign a new carrier with an ID that is already used by other carrier on the same line"},{"location":"protocol-documentation.html#responsecommandstatus","title":"Response.Command.Status","text":"Name Number Description COMMAND_STATUS_UNSPECIFIED 0 This command status is unused, and will never be returned. It is reserved as the default status code according to protobuf specification. COMMAND_STATUS_PROGRESSING 1 Command currently executing. COMMAND_STATUS_COMPLETED 2 Command completed. COMMAND_STATUS_FAILED 3 Command execution failed."},{"location":"protocol-documentation.html#responselinecarrierstatestate","title":"Response.Line.Carrier.State.State","text":"Name Number Description CARRIER_STATE_NONE 0 CARRIER_STATE_CALIBRATING 1 Carrier is currently operating for line calibration. CARRIER_STATE_CALIBRATE_COMPLETED 2 Carrier has completed line calibration, and may now be used for normal operation. CARRIER_STATE_MOVING 3 Carrier is currently moving towards target destination. CARRIER_STATE_MOVE_COMPLETED 4 Carrier has arrived within threshold at target destination. CARRIER_STATE_INITIALIZING 5 Carrier is initializing. Must not be used until initialization is completed. CARRIER_STATE_INITIALIZE_COMPLETED 6 Carrier initialization completed. May now be used for normal operation. CARRIER_STATE_PUSHING 7 Carrier is being pushed by axis. Used to eject carrier from line. CARRIER_STATE_PULLING 9 Carrier is being pulled by axis. Must not be used until pull is completed. CARRIER_STATE_OVERCURRENT 11 Overcurrent detected in carrier axis motor. Carrier movement has been canceled."},{"location":"protocol-documentation.html#scalar-value-types","title":"Scalar Value Types","text":".proto Type Notes C++ Java Python Go C# PHP Ruby double double double float float64 double float Float float float float float float32 float float Float int32 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint32 instead. int32 int int int32 int integer Bignum or Fixnum (as required) int64 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint64 instead. int64 long int/long int64 long integer/string Bignum uint32 Uses variable-length encoding. uint32 int int/long uint32 uint integer Bignum or Fixnum (as required) uint64 Uses variable-length encoding. uint64 long int/long uint64 ulong integer/string Bignum or Fixnum (as required) sint32 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int32s. int32 int int int32 int integer Bignum or Fixnum (as required) sint64 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int64s. int64 long int/long int64 long integer/string Bignum fixed32 Always four bytes. More efficient than uint32 if values are often greater than 2^28. uint32 int int uint32 uint integer Bignum or Fixnum (as required) fixed64 Always eight bytes. More efficient than uint64 if values are often greater than 2^56. uint64 long int/long uint64 ulong integer/string Bignum sfixed32 Always four bytes. int32 int int int32 int integer Bignum or Fixnum (as required) sfixed64 Always eight bytes. int64 long int/long int64 long integer/string Bignum bool bool boolean boolean bool bool boolean TrueClass/FalseClass string A string must always contain UTF-8 encoded or 7-bit ASCII text. string String str/unicode string string string String (UTF-8) bytes May contain any arbitrary sequence of bytes. string ByteString str []byte ByteString string String (ASCII-8BIT)"}]} \ No newline at end of file +{"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"],"fields":{"title":{"boost":1000.0},"text":{"boost":1.0},"tags":{"boost":1000000.0}}},"docs":[{"location":"index.html","title":"PMF MMC system","text":"

PMF provides the Motion Motor Control (MMC) system for controlling Linear Motor Systems (LMS) with ease and high precision.

"},{"location":"index.html#getting-started","title":"Getting started","text":""},{"location":"index.html#mmc-server","title":"MMC Server","text":"

The MMC Server acts as an endpoint that allows multiple clients to interface with the LMS. The server must run on a PC connected to the first driver of the LMS. Contact our engineers to obtain the MMC Server files and organize them as follows:

mmc-server\n\u251c\u2500 config.json5\n\u251c\u2500 mmc.exe\n\u2514\u2500 mmc.pdb\n
Navigate to the mmc-server folder and run the executable:
mmc.exe --log_level=info\n

"},{"location":"index.html#mmc-api","title":"MMC-API","text":"

Our API is built with Protobuf, offering cross-language compatibility to support your programming language of choice. To integrate our API into your program, ensure your working environment supports Protobuf. For complete integration instructions, see the MMC-API Guidelines page.

"},{"location":"index.html#conventions","title":"Conventions","text":"

This section defines the terminology used throughout the PMF MMC documentation.

"},{"location":"index.html#system-hierarchy","title":"System Hierarchy","text":"

The following terms apply to the PMF MMC system:

"},{"location":"index.html#id-constraints","title":"ID Constraints","text":"

Important: ID Indexing

All system IDs (Lines, Drivers, Axes, and Carriers) use 1-based indexing. The first ID is always 1.

Entity Max ID Calculation / Notes Line 256 Maximum number of lines supported per track. Driver 256 Maximum number of drivers per line. Axis 768 Based on 256 drivers \u00d7 3 axes per driver. Carrier 768 Maximum number of moveable magnets per line."},{"location":"changelog.html","title":"Changelog","text":"

All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

"},{"location":"changelog.html#200-2026-03-16","title":"2.0.0 - 2026-03-16","text":""},{"location":"changelog.html#added","title":"Added","text":""},{"location":"changelog.html#changed","title":"Changed","text":""},{"location":"changelog.html#removed","title":"Removed","text":""},{"location":"changelog.html#fixed","title":"Fixed","text":""},{"location":"changelog.html#121-2026-01-21","title":"1.2.1 - 2026-01-21","text":""},{"location":"mmc-api.html","title":"MMC-API Guidelines","text":"

This page covers how to use MMC-API to operate on LMS connected to PMF's MMC system.

"},{"location":"mmc-api.html#mmc-api-structure","title":"MMC-API Structure","text":"

The MMC API consists of three categories: core, command, and info. Each category contains corresponding requests and responses. Please refer to the protocol documentation page for the expected response for each request.

"},{"location":"mmc-api.html#mmc-core","title":"MMC Core","text":"

Use MMC core messages to retrieve server information and track configuration. PMF recommends that clients verify compatibility with the server API version before operation. Starting from version 2.0.0, breaking changes may occur between major versions, therefore clients must ensure they are compatible with the server's API version. Mismatched versions may result in invalid requests or undefined behavior. Clients must fetch the track configuration prior to operating the PMF MMC system to ensure all messages passed to the server contain valid parameters. Refer to the MMC core documentation for a comprehensive list of message types and expected responses.

"},{"location":"mmc-api.html#mmc-command","title":"MMC Command","text":"

Use MMC command messages to operate the PMF MMC system. Clients must use the following rules when sending MMC command messages.

Monitor command status via the command info request defined in the MMC Info section. A list of commands are available on MMC command documentation.

"},{"location":"mmc-api.html#mmc-info","title":"MMC Info","text":"

Use MMC info messages to monitor the real-time state of the track and command status. The client can specify which track information to request by enabling the relevant flags within the track info message definition. The API also allows filtering track info based on driver range, axis range, or specific carrier IDs. Refer to the MMC info documentation for the complete message definitions used to request track and command states.

"},{"location":"mmc-api.html#create-request","title":"Create Request","text":"

This section demonstrates how to construct and encode a request for transmission. The first example illustrates how to decode and validate a response before use. Subsequent examples will omit the response processing logic to focus on request creation and key considerations for specific commands.

Info

Client must exclusively use the mmc.Request message type to send requests to the server. The server always returns an mmc.Response message to be decoded on client side. Any other message sent to server will return mmc.Response.request_error, showing the message is invalid.

"},{"location":"mmc-api.html#requesting-core-information","title":"Requesting Core Information","text":"

Info

A core request message contains only one enum field. The following example demonstrates how to request the API version used by the server. Other core requests are implemented in the same manner.

Warning

Sending a core request with kind CORE_REQUEST_KIND_SERVER_INFO will always return mmc.Response.core.request_error.

zigpython

Tip

Zig users can directly use the pmotionf/mmc-api repository for ease of integration. If you are using a different Zig version, generate the Zig files from the source Protobuf files using zig-protobuf library.

const api = @import(\"mmc-api\");\n// Create a request and encode the message. Encode with passing the\n// transport writer interface pointer and allocator. Send the message by \n// flush the writer..\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .core = .{ .kind = .CORE_REQUEST_KIND_SERVER_INFO },\n    },\n};\ntry request.encode(&writer.interface, allocator);\ntry writer.interface.flush();\n// Receive and decode the message by passing the reader interface pointer \n// and allocator.\nconst decoded: api.protobuf.mmc.Response = try .decode(\n    &client.reader.interface,\n    client.allocator,\n);\nswitch (decoded.body orelse std.log.err(\"Invalid Response\",.{})) {\n    .core => |core_resp| switch (core_resp.body orelse\n        std.log.err(\"Invalid Response\",.{})) {\n        .server => |server| std.log.info(\n              \"Server API version: {}.{}.{}\",\n              .{server.api.major, server.api.minor, server.api.patch,}\n          ),\n          .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n          else => std.log.err(\"Invalid Response\",.{}),\n    },\n    .request_error => |req_err| std.log.err(\"{t}\",.{req_err}),\n    else => std.log.err(\"Invalid Response\",.{}),\n};\n
import mmc_pb2 as mmc\n\n# Snipped: Create and connect socket to server\n\n# Create a request message\nrequest = mmc.Request()\nrequest.core.kind = mmc.mmc_dot_core__pb2.Request.CORE_REQUEST_KIND_SERVER_INFO\n\n# Snipped: Send and receive the message\n\n# Parse response\nmsg = mmc.Response()\nmsg.ParseFromString(response)\n\n# Validate and use the response accordingly\nif msg.WhichOneof(\"body\") == \"request_error\":\n    print(\"Error: \", mmc.Request.Error.Name(msg.request_error))\nelif msg.WhichOneof(\"body\") == \"core\":\n    # Validate if the core response that we receive is `api_version`\n    if msg.core.WhichOneof(\"body\") == \"request_error\":\n        print(\n            \"Error: \",\n            mmc.mmc_dot_core__pb2.Request.Error.Name(msg.core.request_error),\n        )\n    elif msg.core.WhichOneof(\"body\") == \"server\":\n        api = msg.core.server.api\n        print(\n            f\"Server API Version: {api.major}.{api.minor}.{api.patch}\"\n      )\n    else:\n        print(\"Invalid Response\")\nelse:\n    print(\"Invalid Response\")\n\ns.close()\n
"},{"location":"mmc-api.html#command-request","title":"Command Request","text":"

Mandatory Command Cleanup

Every command request returns a unique Command ID. The client is required to:

  1. Track the command status using this ID.
  2. Invoke remove_command once the state reaches COMPLETED or FAILED.

Failure to remove finished commands will block the server queue and prevent further command execution.

Check Error Reason

If the command status is FAILED, users can find a descriptive reason by checking the command's error field.

"},{"location":"mmc-api.html#initialize-carrier","title":"Initialize Carrier","text":"

Info

A carrier must be initialized before any actions can be performed. The initialize command is one of many available methods for initializing carriers. This command is sent to the axis specified by the axis parameter.

Unique Carrier ID Requirement

The client must ensure the carrier_id is unique across the entire line. If the ID is already in use by another initialized carrier on the same line, the server will return CONFLICTING_CARRIER_ID.

Example

The following request initializes an uninitialized carrier with ID 1 on the first line in the forward direction. This carrier's position is on top of axis 1 and axis 2.

zigpython
const api = @import(\"mmc-api\");\n\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .initialize = .{\n                    .line = 1,\n                    .axis = 2,\n                    .carrier = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .link_axis = .DIRECTION_FORWARD,\n                },\n            },\n        },\n    },\n};\n// Snipped content: \n// - Send `initialize` command\n// - Receive command ID as the response of command request\n// - Track command state until state `COMPLETED`\n// - Send `remove_command` command\n// - Receive `removed_id` response as the response of `remove_command` request\n
import mmc_pb2 as mmc\n\n# Creating a request message\nCommand = mmc.mmc_dot_command__pb2.Request()\nrequest = mmc.Request()\nrequest.command.initialize.line = 1\nrequest.command.initialize.axis = 2\nrequest.command.initialize.carrier = 1\nrequest.command.initialize.direction = Command.Direction.DIRECTION_FORWARD\nrequest.command.initialize.link_axis = Command.Direction.DIRECTION_BACKWARD\n# Snipped content: \n# - Send `initialize` command\n# - Receive command ID as the response of command request\n# - Track command state until state `COMPLETED`\n# - Send `remove_command` command\n# - Receive `removed_id` response as the response of `remove_command` request\n
"},{"location":"mmc-api.html#auto-initialize-carriers","title":"Auto Initialize Carriers","text":"

Info

Auto initialize all carriers on the specified lines simultaneously. This process operates on carrier clusters, where a cluster is defined as a group of uninitialized carriers located on adjacent axis.

Warning

Each cluster requires at least one free axis to successfully perform the auto-initialization. Any cluster lacking a free axis will be ignored, and all carriers within that cluster will remain uninitialized upon command completion.

Tip

Ignore the acceleration and velocity fields to use the default values. The default value are:

Example

Auto initialize all carriers on line 1 and line 2.

zigpython
const api = @import(\"mmc-api\");\n\n// Allocate lines\nvar lines: std.ArrayList(\n    api.protobuf.mmc.command.Request.AutoInitialize.Line,\n) = .empty;\ndefer lines.deinit(allocator);\n\n// Define first line\ntry lines.append(allocator, .{\n    .line = 1,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Define second line\ntry lines.append(allocator, .{\n    .line = 2,\n    .acceleration = 6000,\n    .velocity = 600,\n});\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .auto_initialize = .{\n                    .lines = lines,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n\n# Define first line\nline1 = Command.AutoInitialize.Line()\nline1.line = 1\nline1.velocity = 600\nline1.acceleration = 6000\n\n# Define second line\nline2 = Command.AutoInitialize.Line()\nline2.line = 2\nline2.velocity = 600\nline2.acceleration = 6000\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.auto_initialize.lines.append(line1)\nrequest.command.auto_initialize.lines.append(line2)\n
"},{"location":"mmc-api.html#deinitialize-carriers","title":"Deinitialize Carriers","text":"

Info

Deinitialize will release motor control on the specified carriers and remove carrier states from MMC system. Deinitialize all carriers on a line by not specifying a target. If a target is specified, carriers are deinitialized based on that target:

Example

Deinitialize carrier 1 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .deinitialize = .{\n                    .line = line.id,\n                    .target = .{ .carrier = 1 }\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.deinitialize.line = 1\nrequest.command.deinitialize.carrier = 1\n
"},{"location":"mmc-api.html#move-carrier","title":"Move Carrier","text":"

Tip

Track the carrier state until it reaches MOVE_COMPLETED before sending further commands to the specified carrier to avoid unwanted behavior. The command state COMPLETED only indicates that the command was successfully received and is being processed by the MMC system.

Warning

The target field must be specified by the user, and only the last target value will be serialized to the server. See Oneof for complete a description on Oneof protobuf type.

Example

Move initialized carrier 1 to axis 3 on the second line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .move = .{\n                    .line = 2,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .target = .{.axis = 3},\n                    .control = .CONTROL_POSITION,\n                    .disable_cas = false,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.move.line = 2\nrequest.command.move.carrier = 1\nrequest.command.move.velocity = 1000\nrequest.command.move.acceleration = 6000\nrequest.command.move.axis = 3\n# mmc.Control() message is not generated by protoc compiler because Python does\n# not allow to use definition based on namespace.\n# 1 for CONTROL_POSITION\n# 2 for CONTROL_VELOCITY.\nrequest.command.move.control = 1\nrequest.command.move.disable_cas = False\n
"},{"location":"mmc-api.html#push","title":"Push","text":"

Info

Forcefully moves an initialized carrier on the specified axis by one carrier length. Use this movement to cross a line boundary, which deinitializes the carrier from the current line upon completion.

If the carrier field is provided in the push command, the axis enters a pushing state. In this state, the axis remains busy and waits for the specified carrier to arrive; once it arrives, the axis automatically pushes the carrier.

Warning

When pushing the carrier to a different line, the receiving axis on the destination line must be in a pulling state.

Tip

To disable the pushing state on an axis, utilize the stop push command.

Example

Push carrier on axis 1 of line 2 backward to line 1.

Warning

The destination axis on line 1 must be in pulling state.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .push = .{\n                    .line = 2,\n                    .axis = 1,\n                    .direction = .DIRECTION_BACKWARD,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.push.line = 2\nrequest.command.push.axis = 1\nrequest.command.push.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.push.velocity = 1000\nrequest.command.push.acceleration = 6000\n
"},{"location":"mmc-api.html#pull","title":"Pull","text":"

Info

Initialize an incoming carrier located outside the current line. This command puts the specified axis into pulling state. This initialization procedure has the following behavior:

Example

Set axis 6 of line 1 to pulling state, and move the pulled carrier to axis 3.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pull = .{\n                    .line = 1,\n                    .axis = 6,\n                    .carrier = 1,\n                    .velocity = 1000,\n                    .acceleration = 6000,\n                    .direction = .DIRECTION_BACKWARD,\n                    .transition = .{\n                        .control = .CONTROL_POSITION,\n                        .disable_cas = false,\n                        .target = .{.axis = 3},\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\nCommand = mmc.mmc_dot_command__pb2.Request()\n# Create a request\nrequest = mmc.Request()\nrequest.command.pull.line = 1\nrequest.command.pull.axis = 6\nrequest.command.pull.carrier = 1\nrequest.command.pull.direction = Command.Direction.DIRECTION_BACKWARD\nrequest.command.pull.velocity = 1000\nrequest.command.pull.acceleration = 6000\nrequest.command.pull.transition.control = 1\nrequest.command.pull.transition.disable_cas = False\nrequest.command.pull.transition.axis = 3\n
"},{"location":"mmc-api.html#release-carrier","title":"Release Carrier","text":"

Info

Put the initialized carrier into the NONE state, allowing it to be moved manually or by external systems.

Example

Release control of carrier 1 on line 1.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .release = .{\n                    .line = 1,\n                    .target = .{.carrier = 1},\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.release.line = 1\nrequest.command.release.carrier = 1\n
"},{"location":"mmc-api.html#calibrate-line","title":"Calibrate Line","text":"

Info

To calibrate the drivers' configuration on a line, an uninitialized carrier must be located at the center of the first axis

Example

Calibrate the drivers' configuration on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .calibrate = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.calibrate.line = 1\n
"},{"location":"mmc-api.html#stop-push","title":"Stop Push","text":"

Tip

To reset pushing state on all axis, ignore the axes field.

Example

Reset the pushing state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_push = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_push.line = 1\nrequest.command.stop_push.axes.start = 1\nrequest.command.stop_push.axes.end = 4\n
"},{"location":"mmc-api.html#stop-pull","title":"Stop Pull","text":"

Tip

To reset the pulling state on all axes, omit the axes field.

Example

Reset the pulling state on axes 1 to 4 of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop_pull = .{\n                    .line = 1,\n                    .axes = .{\n                        .start = 1,\n                        .end = 4,\n                    },\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop_pull.line = 1\nrequest.command.stop_pull.axes.start = 1\nrequest.command.stop_pull.axes.end = 4\n
"},{"location":"mmc-api.html#set-carrier-id","title":"Set Carrier ID","text":"

Warning

The carrier ID of each carrier must be unique within a line.

Example

Change the carrier ID of carrier 1 to 4 on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_carrier_id = .{\n                    .line = 1,\n                    .carrier = 1,\n                    .new_carrier = 4,\n                },\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_carrier_id.line = 1\nrequest.command.set_carrier_id.carrier = 1\nrequest.command.set_carrier_id.new_carrier = 4\n
"},{"location":"mmc-api.html#set-zero","title":"Set Zero","text":"

Example

Set the zero point of the first line.

Warning

An initialized carrier must be located on the first axis of the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .set_zero = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.set_zero.line = 1\n
"},{"location":"mmc-api.html#clear-errors","title":"Clear Errors","text":"

Warning

Always clear errors whenever an error is detected on an axis or driver. Failing to clear errors may result in unwanted behavior.

Tip

Ignore the axes field to clear errors on all drivers and axes on the line.

Example

Clear all errors on the first line.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .clear_errors = .{.line = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.clear_errors.line = 1\n
"},{"location":"mmc-api.html#emergency-stop","title":"Emergency Stop","text":"

Tip

Pass an empty list to stop operations on all lines.

Example

Stop operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .stop = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.stop.lines.extend([])\n
"},{"location":"mmc-api.html#pause-execution","title":"Pause Execution","text":"

Tip

Pass empty list to pause operations on all lines.

Example

Pause operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .pause = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.pause.lines.extend([])\n
"},{"location":"mmc-api.html#resume-execution","title":"Resume Execution","text":"

Tip

Pass an empty list to resume operation on all lines.

Example

Resume operations on all lines.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .@\"resume\" = .{.lines = &.{}},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Create a request\nrequest = mmc.Request()\nrequest.command.resume.lines.extend([])\n
"},{"location":"mmc-api.html#remove-command","title":"Remove Command","text":"

Warning

Failure to remove a command will block the queue and prevent the server from accepting further commands.

Tip

Always check the command status after sending a command message. (Request Command State)

Example

Remove the command with ID 1 from the server.

zigpython
const api = @import(\"mmc-api\");\n\n// Create a request\nconst request: api.protobuf.mmc.Request = .{\n    .body = .{\n        .command = .{\n            .body = .{\n                .remove_command = .{.command = 1},\n            },\n        },\n    },\n};\n
import mmc_pb2 as mmc\n\n# Creating a request message\nrequest = mmc.Request()\nrequest.command.remove_command.command = id\n
"},{"location":"mmc-api.html#info-request","title":"Info Request","text":""},{"location":"mmc-api.html#request-command-state","title":"Request Command State","text":"

Example

Wait till the command state becomes COMPLETED or FAILED, then remove the command.

zigpython
const api = @import(\"mmc-api\");\n\nfn waitCommand(id: u32) !void {\n    defer removeCommand(id);\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .command = .{ .id = id },\n                },\n            },\n        },\n    };\n    while (true) {\n        try request.encode(&writer.interface, allocator);\n        try writer.interface.flush();\n        var decoded: api.protobuf.mmc.Response = try .decode(\n            &reader.interface,\n            allocator,\n        );\n        defer decoded.deinit(allocator);\n        const command_response = switch (decoded.body orelse\n            return error.InvalidResponse) {\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n                return;\n            },\n            .info => |info_resp| switch (info_resp.body orelse\n                return error.InvalidResponse) {\n                .command => |commands_resp| commands_resp.items.items[0],\n                .request_error => |req_err| {\n                    std.log.err(\"{t}\", .{req_err});\n                    return;\n                },\n                else => return error.InvalidResponse,\n            },\n            else => return error.InvalidResponse,\n        };\n        switch (command_response.status) {\n            .COMMAND_STATUS_PROGRESSING => {}, // continue the loop\n            .COMMAND_STATUS_COMPLETED => return,\n            .COMMAND_STATUS_FAILED => {\n                std.log.err(\"{t}\", .{command_response.@\"error\".?});\n                return;\n            },\n            .COMMAND_STATUS_UNSPECIFIED => return error.InvalidResponse,\n        }\n    }\n}\n
import mmc_pb2 as mmc\n\ndef waitCommand(id):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.command.id = id\n    while True:\n        # Send and receive response\n        s.sendall(request.SerializeToString())\n        response = s.recv(4096)\n\n        # Parsing the response\n        msg = mmc.Response()\n        msg.ParseFromString(response)\n        Command = mmc.mmc_dot_info__pb2.Response.Command()\n\n        # Validate and use the response accordingly\n        if msg.WhichOneof(\"body\") == \"request_error\":\n            print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n            return\n        elif msg.WhichOneof(\"body\") == \"info\":\n            # Validate if the core response that we receive is `api_version`\n            if msg.info.WhichOneof(\"body\") == \"request_error\":\n                print(\n                    \"Request Error\",\n                    mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n                )\n                return\n            elif msg.info.WhichOneof(\"body\") == \"command\":\n                command = msg.info.command.items[0]\n                if command.status == Command.Status.COMMAND_STATUS_COMPLETED:\n                    removeCommand(id)\n                    return\n                elif command.status == Command.Status.COMMAND_STATUS_FAILED:\n                    removeCommand(id)\n                    raise Exception(Command.Error.Name(command.error))\n                else:\n                    print(\"Invalid Response\")\n                    return\n            else:\n                print(\"Invalid Response\")\n                return\n        else:\n            print(\"Invalid Response\")\n            return\n
"},{"location":"mmc-api.html#request-track-state","title":"Request Track State","text":"

Tip

Certain commands require the client to monitor carrier status to ensure movement is completed.

Warning

Monitor the error flags of driver, axis and carriers to prevent damage to the motor or driver board. Pay close attention to inverter_overheat on the driver and overcurrent flags on the axis; immediately deinitialize any carrier on the affected axes and drivers if these are detected. The overvoltage and undervoltage flags indicate that the system voltage supply may have a problem; please consult with our engineers to resolve the issue.

Request carrier state

Tip

zigpython
const api = @import(\"mmc-api\");\nfn carrierState(line: u32, carrier: u32) !void {\n    var carrier_id = [1]u32{carrier};\n    const request: api.protobuf.mmc.Request = .{\n        .body = .{\n            .info = .{\n                .body = .{\n                    .track = .{\n                        .line = line,\n                        .info_carrier_state = true,\n                        .filter = .{\n                            .carriers = .{\n                                .ids = .fromOwnedSlice(&carrier_id),\n                            },\n                        },\n                    },\n                },\n            },\n        },\n    };\n    try request.encode(&writer.interface, allocator);\n    try writer.interface.flush();\n    var decoded: api.protobuf.mmc.Response = try .decode(\n        &reader.interface,\n        allocator,\n    );\n    defer decoded.deinit(allocator);\n    switch (decoded.body orelse return error.InvalidResponse) {\n        .info => |info_resp| switch (info_resp.body orelse\n            return error.InvalidResponse) {\n            .track => |track_resp| {\n                std.log.info(\"{}\", .{track_resp.carrier_state.items[0]});\n            },\n            .request_error => |req_err| {\n                std.log.err(\"{t}\", .{req_err});\n            },\n            else => return error.InvalidResponse,\n        },\n        .request_error => |req_err| {\n            std.log.err(\"{t}\", .{req_err});\n            return;\n        },\n        else => return error.InvalidResponse,\n    }\n}\n
import mmc_pb2 as mmc\ndef carrierState(line, carrier):\n    # Creating a request message\n    request = mmc.Request()\n    request.info.track.line = line\n    request.info.track.info_carrier_state = True\n    request.info.track.carriers.ids.append(carrier)\n\n    # Parsing the response\n    msg = mmc.Response()\n    msg.ParseFromString(response)\n    # Validate and use the response accordingly\n    if msg.WhichOneof(\"body\") == \"request_error\":\n        print(\"Request Error\", mmc.Request.Error.Name(msg.request_error))\n    elif msg.WhichOneof(\"body\") == \"info\":\n        # Validate if the core response that we receive is `api_version`\n        if msg.info.WhichOneof(\"body\") == \"request_error\":\n            print(\n                \"Request Error\",\n                mmc.mmc_dot_info__pb2.Request.Error.Name(msg.info.request_error),\n            )\n        elif msg.info.WhichOneof(\"body\") == \"track\":\n            assert len(msg.info.track.carrier_state) != 0\n            carrier = msg.info.track.carrier_state[0]\n            print(carrier)\n        else:\n            print(\"Invalid Response\")\n    else:\n        print(\"Invalid Response\")\n
"},{"location":"protocol-documentation.html","title":"Protocol Documentation","text":""},{"location":"protocol-documentation.html#table-of-contents","title":"Table of Contents","text":"

Top

"},{"location":"protocol-documentation.html#mmcproto","title":"mmc.proto","text":""},{"location":"protocol-documentation.html#request","title":"Request","text":"

Request message. All client-to-server messages should be of this message type.

Field Type Label Description core core.Request Core request. Used to retrieve information about the server or the configured track. command command.Request Command request. Used to send and manage commands to the server, which will execute commands on the connected track. info info.Request Info request. Used to retrieve information about track state or commands processed by the server.

"},{"location":"protocol-documentation.html#response","title":"Response","text":"

Response message. All server-to-client messages will be of this message type.

Field Type Label Description core core.Response Core response. command command.Response Command response. info info.Response Info Response. request_error Request.Error Top-level request error. This error field will be returned only if the top-level request could not be handled properly. Otherwise, response kinds may contain more specific error codes.

"},{"location":"protocol-documentation.html#requesterror","title":"Request.Error","text":"Name Number Description MMC_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. MMC_REQUEST_ERROR_INVALID_MESSAGE 1 The request could not be decoded as a valid protobuf message.

Top

"},{"location":"protocol-documentation.html#rangeproto","title":"range.proto","text":""},{"location":"protocol-documentation.html#range","title":"Range","text":"Field Type Label Description start uint32 Start of range, inclusive. end uint32 End of range, inclusive.

Top

"},{"location":"protocol-documentation.html#mmccommandproto","title":"mmc/command.proto","text":""},{"location":"protocol-documentation.html#request_1","title":"Request","text":"

Command API: List of commands to operate the PMF's motion system.

When a command is sent to the server, it will be queued for execution. Command execution status can be polled through the Info API. The status remains stored in a limited history buffer, and should be cleared with remove_command after completion.

Field Type Label Description calibrate Request.Calibrate Calibrate a line. This command only needs to be run once after hardware setup; calibrated values will remain stored in drivers even after a power cycle. set_zero Request.SetZero Set the zero position of the specified line. This command can be run optionally after calibration, upon which all drivers will store the set zero position of the line. The set zero position will remain unchanged even after a power cycle. initialize Request.Initialize Initialize a carrier. Carriers must be initialized before they can be moved. Initialization is required after every power cycle. auto_initialize Request.AutoInitialize Initialize all carriers of the specified line(s). If no lines are specified, initialize all carriers across all lines in the track. deinitialize Request.Deinitialize Deinitialize a carrier. This removes all carrier information, such as recognized position and carrier ID. move Request.Move Move an initialized carrier to the desired position. pull Request.Pull Pull and initialize a new carrier into a line. push Request.Push Push an initialized carrier to the specified direction. stop_pull Request.StopPull Stop waiting to pull a new carrier at an axis. stop_push Request.StopPush Stop waiting to push an initialized carrier at an axis. release Request.Release Release the motor control of a carrier. clear_errors Request.ClearErrors Clear all errors within the specified driver range. remove_command Request.RemoveCommand Cancel a running command or remove its status history. stop Request.Stop Activate emergency stop for all drivers in line(s). Emergency stop will cause all carriers to decelerate to rest, then reset all carriers' movement commands. pause Request.Pause Activate pause for all drivers in line(s). Pause will cause all carriers to decelerate to rest. On resume, the carriers will continue their previously assigned movement commands. resume Request.Resume Deactivate emergency stop and pause for all drivers in line(s). set_carrier_id Request.SetCarrierId Change an existing carrier ID to a new unique carrier ID.

"},{"location":"protocol-documentation.html#requestautoinitialize","title":"Request.AutoInitialize","text":"

Automatically initialize carriers on every specified lines.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines Request.AutoInitialize.Line repeated

"},{"location":"protocol-documentation.html#requestautoinitializeline","title":"Request.AutoInitialize.Line","text":"Field Type Label Description line uint32 Line ID. velocity float optional Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s (default 600 mm/s). acceleration float optional Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2 (default 6000 mm/s^2)."},{"location":"protocol-documentation.html#requestcalibrate","title":"Request.Calibrate","text":"

Calibrate a line by positioning an uninitialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requestclearerrors","title":"Request.ClearErrors","text":"

Clear all error information on the driver. If a target is specified, clear error information of drivers included in that target. If not, clear error information on all drivers of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. drivers Range Driver ID range. axes Range Axis ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestdeinitialize","title":"Request.Deinitialize","text":"

Clear carrier information located on the axis. If a target is specified, clear information of carriers included in that target. If not, clear all carrier information of the specified line ID.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range Axis ID range. drivers Range Driver ID range. carrier uint32 Carrier ID.

"},{"location":"protocol-documentation.html#requestinitialize","title":"Request.Initialize","text":"

Initialize a carrier.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the new carrier. direction Request.Direction Initialization direction for the new carrier. link_axis Request.Direction optional Linked axis direction from the specified axis.

"},{"location":"protocol-documentation.html#requestmove","title":"Request.Move","text":"

Move a carrier to the desired position.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. axis uint32 Move carrier to the center of the axis. location float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. distance float Move carrier to relative distance to current carrier position. Negative distance moves the carrier backwards. control mmc.Control Control method for moving carrier. disable_cas bool Disable the carrier's collision avoidance system (CAS).

"},{"location":"protocol-documentation.html#requestpause","title":"Request.Pause","text":"

Pause any operation in PMF LMS. Any queued commands in the server will be continued once the resume command is given.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, pause operations only on the specified lines.

"},{"location":"protocol-documentation.html#requestpull","title":"Request.Pull","text":"

Pull and initialize a new carrier into a line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. carrier uint32 ID for the incoming carrier. direction Request.Direction The direction from which the incoming carrier is moving. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. When the transition location target is set to NaN, the velocity must be 0. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. When the transition location target is set to NaN, the acceleration must be 0. transition Request.Pull.Transition optional Smoothly transition to carrier movement after pull completion.

"},{"location":"protocol-documentation.html#requestpulltransition","title":"Request.Pull.Transition","text":"Field Type Label Description control mmc.Control Control method for moving carrier. disable_cas bool Disabling the carrier's collision avoidance system (CAS). target float Move carrier to relative location to the zero-point of the line, which is set by default at the center of the line's first axis after calibration, but can also be set with the SetZero command. Pass NaN to pull carrier without motor control, allowing carrier to be pulled with external force."},{"location":"protocol-documentation.html#requestpush","title":"Request.Push","text":"

Push an initialized carrier to the specified direction.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axis uint32 Axis ID. direction Request.Direction Direction of carrier movement. velocity float Velocity of carrier movement. Floating point with range 0.1 - 6,000 mm/s. acceleration float Acceleration of carrier movement. Floating point with range 100 - 24,500 mm/s^2. carrier uint32 optional Carrier ID. If provided, wait for the specified carrier at the axis and push it once the carrier arrives.

"},{"location":"protocol-documentation.html#requestrelease","title":"Request.Release","text":"

Release the control imposed by the motor to the carrier. If a target is specified, all motors included in that target release control. Otherwise, all carriers on the provided line will be released from control.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Carrier ID. axes Range Axis ID range. drivers Range Driver ID range.

"},{"location":"protocol-documentation.html#requestremovecommand","title":"Request.RemoveCommand","text":"

Remove a command on the server if the command ID is specified. If no command ID is specified, remove any commands received by the server. If the commands are still progressing, cancel the command execution.

Expected response: mmc.Response.body.command.body.removed_id (uint32).

Field Type Label Description command uint32 optional Command ID.

"},{"location":"protocol-documentation.html#requestresume","title":"Request.Resume","text":"

Resume lines that have been stopped or paused. If the line is not paused or emergency stopped, this command will succeed without any effect.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, resume operations only to those specified lines.

"},{"location":"protocol-documentation.html#requestsetcarrierid","title":"Request.SetCarrierId","text":"

Change the carrier ID of an existing initialized carrier. If the new carrier ID already exists on the line, returns INVALID_CARRIER.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. carrier uint32 Target existing initialized carrier ID. new_carrier uint32 New desired carrier ID (unique in line).

"},{"location":"protocol-documentation.html#requestsetzero","title":"Request.SetZero","text":"

Set a zero position of a line by positioning an initialized carrier on the first axis of the line.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID.

"},{"location":"protocol-documentation.html#requeststop","title":"Request.Stop","text":"

Send an emergency stop command to stop any operation in PMF LMS. This command also removes all queued commands in the server.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description lines uint32 repeated Line ID. If provided, stop operations only on the specified lines and remove all commands that targeting those lines.

"},{"location":"protocol-documentation.html#requeststoppull","title":"Request.StopPull","text":"

Stop pulling a carrier to the specified axis. If no axis is provided, then all pending carrier pulls on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#requeststoppush","title":"Request.StopPush","text":"

Stop pushing a carrier from the specified axis. If no axis is provided, then all pending carrier pushes on the line will be stopped.

Expected response: mmc.Response.body.command.body.id (uint32).

Field Type Label Description line uint32 Line ID. axes Range optional Axis ID range.

"},{"location":"protocol-documentation.html#response_1","title":"Response","text":"

Response description to the command API.

Field Type Label Description id uint32 Assigned ID for newly sent command. removed_id uint32 ID of cleared existing command. request_error Request.Error Error during command's execution.

"},{"location":"protocol-documentation.html#requestdirection","title":"Request.Direction","text":"Name Number Description DIRECTION_UNSPECIFIED 0 DIRECTION_BACKWARD 1 DIRECTION_FORWARD 2"},{"location":"protocol-documentation.html#requesterror_1","title":"Request.Error","text":"Name Number Description COMMAND_REQUEST_ERROR_UNSPECIFIED 0 COMMAND_REQUEST_ERROR_INVALID_LINE 1 Attempted to use line ID outside of the configured lines. COMMAND_REQUEST_ERROR_INVALID_AXIS 2 Attempted to use axis ID outside of the configured axes of the line. COMMAND_REQUEST_ERROR_INVALID_DRIVER 3 Attempted to use driver ID outside of the configured drivers of the line. COMMAND_REQUEST_ERROR_INVALID_ACCELERATION 4 Attempted to use acceleration value outside of 1-245. COMMAND_REQUEST_ERROR_INVALID_VELOCITY 5 Attempted to use velocity value outside of 1-60. COMMAND_REQUEST_ERROR_INVALID_DIRECTION 6 Using invalid direction for the command. COMMAND_REQUEST_ERROR_INVALID_LOCATION 7 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_DISTANCE 8 Deprecated. Check COMMAND_ERROR_INVALID_CARRIER_TARGET on Info.Response.Command.Error. COMMAND_REQUEST_ERROR_INVALID_CARRIER 9 Attempted to send a command to carrier outside of 1-2048. COMMAND_REQUEST_ERROR_MISSING_PARAMETER 10 A command missing the required parameter. COMMAND_REQUEST_ERROR_COMMAND_NOT_FOUND 11 Attempted to remove or cancel a non-existing command. COMMAND_REQUEST_ERROR_CARRIER_NOT_FOUND 12 Attempted to send command to an uninitialized carrier. COMMAND_REQUEST_ERROR_OUT_OF_MEMORY 14 Server unable to receive new command caused by out of memory. Try Command.Request.remove_command to free the memory. COMMAND_REQUEST_ERROR_MAXIMUM_AUTO_INITIALIZE_EXCEEDED 15 Attempted to run more than 8 auto initialize instance. COMMAND_REQUEST_ERROR_CONFLICTING_CARRIER_ID 16 Attempted to assign a carrier ID that is already used by another carrier on the same line. COMMAND_REQUEST_ERROR_INVALID_COMMAND 17 Command index is out of bounds for the configured command status buffer.

Top

"},{"location":"protocol-documentation.html#mmccontrolproto","title":"mmc/control.proto","text":""},{"location":"protocol-documentation.html#control","title":"Control","text":"

Carrier motor control kind.

Name Number Description CONTROL_UNSPECIFIED 0 CONTROL_POSITION 1 Carrier controlled with position priority. CONTROL_VELOCITY 2 Carrier controlled with velocity priority.

Top

"},{"location":"protocol-documentation.html#mmccoreproto","title":"mmc/core.proto","text":""},{"location":"protocol-documentation.html#request_2","title":"Request","text":"Field Type Label Description kind Request.Kind"},{"location":"protocol-documentation.html#response_2","title":"Response","text":"

Response description to the core API.

Field Type Label Description server Response.Server Server process information. track_config Response.TrackConfig Track configuration. request_error Request.Error Error response if the core request could not be handled.

"},{"location":"protocol-documentation.html#responsesemanticversion","title":"Response.SemanticVersion","text":"Field Type Label Description major uint32 minor uint32 patch uint32"},{"location":"protocol-documentation.html#responseserver","title":"Response.Server","text":"

Server version and name.

Field Type Label Description name string Server name. version Response.SemanticVersion Server implementation version. api Response.SemanticVersion

"},{"location":"protocol-documentation.html#responsetrackconfig","title":"Response.TrackConfig","text":"Field Type Label Description lines Response.TrackConfig.Line repeated All configured lines in track."},{"location":"protocol-documentation.html#responsetrackconfigline","title":"Response.TrackConfig.Line","text":"Field Type Label Description id uint32 Line ID. Numeric ID, starting from 1, that is unique to each line in the track. This ID is used to address the line in other requests. name string Configured line name. This name is otherwise unused by the API, and is provided to the client for end-user convenience. axes uint32 Total number of axes in the line. axis_length float Length of each axis in the line, in millimeters. carrier_length float Carrier dimension parallel to carrier movement, in millimeters. drivers uint32 Total number of drivers in the line. carrier_width float Carrier dimension perpendicular to carrier movement, in millimeters."},{"location":"protocol-documentation.html#requesterror_2","title":"Request.Error","text":"Name Number Description CORE_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. CORE_REQUEST_ERROR_REQUEST_UNKNOWN 1 The core request kind was unspecified."},{"location":"protocol-documentation.html#requestkind","title":"Request.Kind","text":"Name Number Description CORE_REQUEST_KIND_UNSPECIFIED 0 This request kind is unused, and should never be sent. It is reserved as the default request kind according to protobuf specification. CORE_REQUEST_KIND_SERVER_INFO 2 Request server process information. This includes the configured server name and server implementation version. CORE_REQUEST_KIND_TRACK_CONFIG 3 Request the configured track information of the server.

Top

"},{"location":"protocol-documentation.html#mmcinfoproto","title":"mmc/info.proto","text":""},{"location":"protocol-documentation.html#request_3","title":"Request","text":"Field Type Label Description command Request.Command Command information request. Get current status of command; necessary to determine if command is currently running, completed, or failed. track Request.Track Track information request. Get current track state information."},{"location":"protocol-documentation.html#requestcommand","title":"Request.Command","text":"

Request for status of specified command ID from the server. If no command ID is provided, then request for status of all commands from the server.

Expected response: mmc.Response.body.info.body.commands

Field Type Label Description id uint32 optional

"},{"location":"protocol-documentation.html#requesttrack","title":"Request.Track","text":"

Request track state information from server. One or more of the info_ flags must be enabled to select the kind of track information desired. A filter may be optionally provided to limit the source of information from the track.

Expected response: mmc.Response.body.info.body.track

Field Type Label Description lines uint32 repeated Line ID(s). Select line(s) from which information will be retrieved. info_driver_state bool Retrieve driver state information. info_driver_errors bool Retrieve driver error information. info_axis_state bool Retrieve axis state information. info_axis_errors bool Retrieve axis errors information. info_carrier_state bool Retrieve carrier state information. drivers Range Retrieve information from driver ID range. Driver information flags will include drivers within this range. Axis information flags will include every axis belonging to the drivers in this range. Carrier information flags will include every carrier currently controlled by one of the drivers in this range. axes Range Retrieve information from axis ID range. Driver information flags will include drivers that contain one of the axes within this range. Axis information flags will include axes within this range. Carrier information flags will include every carrier currently controlled by one of the axes in this range. carriers Request.Track.Ids Retrieve information from carrier IDs. Driver information flags will include drivers that control one of the carriers within this list. Axis information flags will include axes that control one of the carriers within this list. Carrier information flags will include carriers within this list.

"},{"location":"protocol-documentation.html#requesttrackids","title":"Request.Track.Ids","text":"

List of IDs. At least one ID must be provided.

Field Type Label Description ids uint32 repeated

"},{"location":"protocol-documentation.html#response_3","title":"Response","text":"Field Type Label Description command Response.Commands Information for requested command(s). If empty, no matching command(s) was found. track Response.Track Information for requested track state. request_error Request.Error Info request error. This error field will be returned if the provided info request could not be handled properly."},{"location":"protocol-documentation.html#responsecommand","title":"Response.Command","text":"Field Type Label Description id uint32 Command ID. Valid IDs begin from 1, and may be reused after command status is cleared from server history. status Response.Command.Status Command status. error Response.Command.Error optional Command error response, only if the status is COMMAND_STATUS_FAILED."},{"location":"protocol-documentation.html#responsecommands","title":"Response.Commands","text":"Field Type Label Description items Response.Command repeated"},{"location":"protocol-documentation.html#responseline","title":"Response.Line","text":"Field Type Label Description id uint32 Line ID. driver_state Response.Line.Driver.State repeated Driver state information list. Empty if request flag was disabled. driver_errors Response.Line.Driver.Error repeated Driver error information list. Empty if request flag was disabled. axis_state Response.Line.Axis.State repeated Axis state information list. Empty if request flag was disabled. axis_errors Response.Line.Axis.Error repeated Axis error information list. Empty if request flag was disabled. carrier_state Response.Line.Carrier.State repeated Carrier state information list. Empty if request flag was disabled."},{"location":"protocol-documentation.html#responselineaxis","title":"Response.Line.Axis","text":""},{"location":"protocol-documentation.html#responselineaxiserror","title":"Response.Line.Axis.Error","text":"Field Type Label Description id uint32 Axis ID. overcurrent bool Motor overcurrent detected. Motor control released to prevent damage."},{"location":"protocol-documentation.html#responselineaxisstate","title":"Response.Line.Axis.State","text":"Field Type Label Description id uint32 Axis ID. motor_active bool Axis is currently controlling a carrier. waiting_pull bool Axis is waiting to pull carrier. waiting_push bool Axis is waiting to push carrier. carrier uint32 Carrier ID; non-zero if an initialized carrier is on the axis. hall_alarm_back bool Axis back hall alarm is active. Magnet is detected above back hall sensor. hall_alarm_front bool Axis front hall alarm is active. Magnet is detected above front hall sensor."},{"location":"protocol-documentation.html#responselinecarrier","title":"Response.Line.Carrier","text":""},{"location":"protocol-documentation.html#responselinecarrierstate","title":"Response.Line.Carrier.State","text":"Field Type Label Description id uint32 Carrier ID. Will always be non-zero. position float Position of the carrier in line, in meters. axis_main uint32 Carrier's primary axis ID. axis_auxiliary uint32 optional Carrier's auxiliary axis ID, if carrier is on top of two axes. cas_disabled bool Collision avoidance system (CAS) disabled. cas_triggered bool Collision avoidance system (CAS) triggered. Carrier will automatically resume movement when path is clear. state Response.Line.Carrier.State.State Carrier state."},{"location":"protocol-documentation.html#responselinedriver","title":"Response.Line.Driver","text":""},{"location":"protocol-documentation.html#responselinedrivererror","title":"Response.Line.Driver.Error","text":"Field Type Label Description id uint32 Driver ID. control_loop_time_exceeded bool Control loop exceeded maximum loop time. inverter_overheat bool Inverter is overheated. undervoltage bool Driver voltage supply too low. overvoltage bool Driver voltage supply too high. comm_error_prev bool Communication error with previous driver in line. comm_error_next bool Communication error with next driver in line."},{"location":"protocol-documentation.html#responselinedriverstate","title":"Response.Line.Driver.State","text":"Field Type Label Description id uint32 Driver ID. connected bool Connection status between driver and server. busy bool Driver is currently executing a command. motor_disabled bool Driver motor release activated. All driver motors are inactive. stopped bool Driver emergency stop activated. paused bool Driver pause activated."},{"location":"protocol-documentation.html#responsetrack","title":"Response.Track","text":"Field Type Label Description lines Response.Line repeated"},{"location":"protocol-documentation.html#requesterror_3","title":"Request.Error","text":"Name Number Description INFO_REQUEST_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. INFO_REQUEST_ERROR_INVALID_LINE 1 Invalid line ID provided. Ensure that line ID exists in track configuration. INFO_REQUEST_ERROR_INVALID_AXIS 2 Invalid axis ID provided. Ensure that axis ID exists in line. INFO_REQUEST_ERROR_INVALID_DRIVER 3 Invalid driver ID provided. Ensure that driver ID exists in line. INFO_REQUEST_ERROR_MISSING_PARAMETER 4 Request is missing a required parameter. Ensure that at least one of the information flag is selected when requesting track information. INFO_REQUEST_ERROR_COMMAND_NOT_FOUND 5 Attempted to request information from a non-existing command. INFO_REQUEST_ERROR_INVALID_COMMAND 6 Command index is out of bounds for the configured command status buffer. INFO_REQUEST_ERROR_INVALID_CARRIER 7 Attempted to send a command to carrier outside of range."},{"location":"protocol-documentation.html#responsecommanderror","title":"Response.Command.Error","text":"Name Number Description COMMAND_ERROR_UNSPECIFIED 0 This error code is unused, and will never be returned. It is reserved as the default error code according to protobuf specification. COMMAND_ERROR_INVALID_SYSTEM_STATE 1 System state prevented successful command execution. Ensure that all preconditions are met with track info request before sending command. COMMAND_ERROR_INVALID_CARRIER_ID 2 Deprecated. Check COMMAND_REQUEST_ERROR_INVALID_CARRIER on Command.Request.Error. COMMAND_ERROR_DRIVER_DISCONNECTED 3 Driver connection failed while command progressing. COMMAND_ERROR_UNEXPECTED 4 Unexpected command execution error. This is likely an implementation bug; please contact PMF support for assistance. COMMAND_ERROR_CARRIER_NOT_FOUND 5 Target carrier is removed while command progressing. COMMAND_ERROR_CARRIER_ALREADY_INITIALIZED 6 Attempted to initialize an initialized carrier. COMMAND_ERROR_DRIVER_STOPPED 7 Target driver is stopped while command progressing. Consider resume the driver before sending further command. COMMAND_ERROR_INVALID_CARRIER_TARGET 8 Carrier targeting a location outside of the configured track. COMMAND_ERROR_CONFLICTING_CARRIER_ID 9 Attempted to assign a new carrier with an ID that is already used by other carrier on the same line"},{"location":"protocol-documentation.html#responsecommandstatus","title":"Response.Command.Status","text":"Name Number Description COMMAND_STATUS_UNSPECIFIED 0 This command status is unused, and will never be returned. It is reserved as the default status code according to protobuf specification. COMMAND_STATUS_PROGRESSING 1 Command currently executing. COMMAND_STATUS_COMPLETED 2 Command completed. COMMAND_STATUS_FAILED 3 Command execution failed."},{"location":"protocol-documentation.html#responselinecarrierstatestate","title":"Response.Line.Carrier.State.State","text":"Name Number Description CARRIER_STATE_NONE 0 CARRIER_STATE_CALIBRATING 1 Carrier is currently operating for line calibration. CARRIER_STATE_CALIBRATE_COMPLETED 2 Carrier has completed line calibration, and may now be used for normal operation. CARRIER_STATE_MOVING 3 Carrier is currently moving towards target destination. CARRIER_STATE_MOVE_COMPLETED 4 Carrier has arrived within threshold at target destination. CARRIER_STATE_INITIALIZING 5 Carrier is initializing. Must not be used until initialization is completed. CARRIER_STATE_INITIALIZE_COMPLETED 6 Carrier initialization completed. May now be used for normal operation. CARRIER_STATE_PUSHING 7 Carrier is being pushed by axis. Used to eject carrier from line. CARRIER_STATE_PULLING 9 Carrier is being pulled by axis. Must not be used until pull is completed. CARRIER_STATE_OVERCURRENT 11 Overcurrent detected in carrier axis motor. Carrier movement has been canceled."},{"location":"protocol-documentation.html#scalar-value-types","title":"Scalar Value Types","text":".proto Type Notes C++ Java Python Go C# PHP Ruby double double double float float64 double float Float float float float float float32 float float Float int32 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint32 instead. int32 int int int32 int integer Bignum or Fixnum (as required) int64 Uses variable-length encoding. Inefficient for encoding negative numbers \u2013 if your field is likely to have negative values, use sint64 instead. int64 long int/long int64 long integer/string Bignum uint32 Uses variable-length encoding. uint32 int int/long uint32 uint integer Bignum or Fixnum (as required) uint64 Uses variable-length encoding. uint64 long int/long uint64 ulong integer/string Bignum or Fixnum (as required) sint32 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int32s. int32 int int int32 int integer Bignum or Fixnum (as required) sint64 Uses variable-length encoding. Signed int value. These more efficiently encode negative numbers than regular int64s. int64 long int/long int64 long integer/string Bignum fixed32 Always four bytes. More efficient than uint32 if values are often greater than 2^28. uint32 int int uint32 uint integer Bignum or Fixnum (as required) fixed64 Always eight bytes. More efficient than uint64 if values are often greater than 2^56. uint64 long int/long uint64 ulong integer/string Bignum sfixed32 Always four bytes. int32 int int int32 int integer Bignum or Fixnum (as required) sfixed64 Always eight bytes. int64 long int/long int64 long integer/string Bignum bool bool boolean boolean bool bool boolean TrueClass/FalseClass string A string must always contain UTF-8 encoded or 7-bit ASCII text. string String str/unicode string string string String (UTF-8) bytes May contain any arbitrary sequence of bytes. string ByteString str []byte ByteString string String (ASCII-8BIT)"}]} \ No newline at end of file diff --git a/site/sitemap.xml.gz b/site/sitemap.xml.gz index 07d697c..b751ac7 100644 Binary files a/site/sitemap.xml.gz and b/site/sitemap.xml.gz differ diff --git a/src/protobuf/mmc/core.pb.zig b/src/protobuf/mmc/core.pb.zig index cb2dc32..a41da3b 100644 --- a/src/protobuf/mmc/core.pb.zig +++ b/src/protobuf/mmc/core.pb.zig @@ -118,6 +118,7 @@ pub const Response = struct { axis_length: f32 = 0, carrier_length: f32 = 0, drivers: u32 = 0, + carrier_width: f32 = 0, pub const _desc_table = .{ .id = fd(1, .{ .scalar = .uint32 }), @@ -126,6 +127,7 @@ pub const Response = struct { .axis_length = fd(4, .{ .scalar = .float }), .carrier_length = fd(5, .{ .scalar = .float }), .drivers = fd(6, .{ .scalar = .uint32 }), + .carrier_width = fd(7, .{ .scalar = .float }), }; pub fn encode(