import { Observable } from 'rxjs'; import { RetryConfig } from 'rxjs/operators'; import { Device } from './device'; import { DeviceParameter } from './device-parameter'; import { HardwareDescription, StackInfo } from './hardware-description'; import { MotionMasterReqResSocket } from './motion-master-req-res-socket'; import { UIFeaturesConfig } from './parameter'; import { SystemLogLine } from './system-log-line'; import { MotionMasterMessage, ParameterValueType, ParameterTypeValue, DeviceParameterValuesStatus, ParameterTypeValueKey, DeviceRefObj, DeviceRef, FullAutoTuningStatus, SystemVersionStatus, DeviceInfoStatus, DeviceParameterInfoStatus, GetDeviceParameterInfoRequest, GetDeviceParameterValuesRequest, GetMultiDeviceParameterValuesRequest, MultiDeviceParameterValuesStatus, SetDeviceParameterValuesRequest, SetMultiDeviceParameterValuesRequest, GetDeviceFileListRequest, DeviceFileListStatus, GetDeviceFileRequest, DeviceFileStatus, SetDeviceFileRequest, DeleteDeviceFileRequest, ResetDeviceFaultRequest, DeviceFaultResetStatus, StopDeviceRequest, DeviceStopStatus, StartDeviceFirmwareInstallationRequest, DeviceFirmwareInstallationStatus, GetDeviceLogRequest, DeviceLogStatus, StartCoggingTorqueRecordingRequest, CoggingTorqueRecordingStatus, GetCoggingTorqueDataRequest, CoggingTorqueDataStatus, StartOffsetDetectionRequest, OffsetDetectionStatus, StartPlantModelIdentificationRequest, PlantIdentificationStatus, ComputeAutoTuningGainsRequest, AutoTuningStatus, SetMotionControllerParametersRequest, MotionControllerStatus, EnableMotionControllerRequest, SetSignalGeneratorParametersRequest, SignalGeneratorStatus, StopSignalGeneratorRequest, StartMonitoringDeviceParameterValuesRequest, MonitoringParameterValuesStatus, StopMonitoringDeviceParameterValuesRequest, GetEthercatNetworkStateRequest, EthercatNetworkStateStatus, SetEthercatNetworkStateRequest, StartNarrowAngleCalibrationRequest, NarrowAngleCalibrationStatus, SetSystemClientTimeoutRequest, StartSystemIdentificationRequest, SystemIdentificationStatus, CirculoEncoderMagnetDistanceStatus, StartCirculoEncoderNarrowAngleCalibrationProcedureRequest, CirculoEncoderNarrowAngleCalibrationProcedureStatus, GetDeviceCiA402StateRequest, DeviceCiA402StateStatus, SetDeviceCiA402StateRequest, SystemLogStatus, StartDeviceSiiRestoreRequest, DeviceSiiRestoreStatus, StartOpenLoopFieldControlRequest, OpenLoopFieldControlStatus, ComputeFullAutoTuningGainsRequest, StartFullAutoTuningRequest, StopFullAutoTuningRequest, StartCirculoEncoderConfigurationRequest, CirculoEncoderConfigurationStatus, StopCirculoEncoderNarrowAngleCalibrationProcedureRequest, StartOsCommandRequest, OsCommandStatus, RestoreDefaultParametersType, DeviceParameterAddressValue, DeviceParameterIds, DeviceParameterInfo, RequestStatusMessage, UiPdoMapping, UiConfig, ExecuteForwardCallRequest, ForwardCallStatus, PlantModel, NotchFilter, LoadConfigStrategy, SystemInformationStatus, SetPdoModeRequest, PdoModeStatus, GetDeviceSiiRequest, DeviceSiiStatus, SmmAutomatedUpdate } from './types'; import { Cia402State, ModesOfOperation } from './cia402'; import { EncoderRegisterCommunicationOsCommandResponse, MotorPhaseOrderDetectionOsCommandResponse, OpenPhaseDetectionOsCommandResponse, OsCommandMode, OsCommandResponse, PhaseResistanceMeasurementOsCommandResponse, PhaseInductanceMeasurementOsCommandResponse, PolePairDetectionOsCommandResponse, CommutationOffsetMeasurementOsCommandResponse, IcMuCalibrationModeOsCommandResponse, OpenLoopFieldModeOsCommandResponse, HrdStreamingOsCommandResponse, TorqueConstantMeasurementOsCommandResponse, SkippedCyclesCounterOsCommandResponse, IgnoreBissStatusBitsOsCommandResponse, SystemIdentificationOsCommandResponse, KublerEncoderCommandOsCommandResponse, UseInternalEncoderVelocityOsCommandResponse, KublerEncoderRegisterCommunicationOsCommandResponse, SmmAcyclicHandlerOsCommandResponse, HrdStreamingOsCommandAction, HrdStreamingOsCommandDataIndex, SmmAcyclicHandlerLoadParametersForVerificationOsCommandResponse, ChirpSignalOptions, OsCommandAbortResult } from './os-command'; import { IntegroVariant } from './integro-variant'; import { ConfigParameter } from './config-file'; import { MotionMasterClientIndexedDB } from './mmcidb'; import { SmmParameter } from './smm'; import { DataType } from 'python-struct'; import { CirculoIntegratedEncoderI2CDeviceId } from './circulo'; import { EncoderRegisterError } from './encoder'; import { IntegroIntegratedEncoderError } from './integro'; import { OffsetDetectionStepId, OffsetDetectionSteps } from './offset-detection'; /** * This class contains methods for making requests to Motion Master using the injected request/response socket. * * Each request message defined in the proto file has a corresponding request method in this class. * For some requests, like firmware installation, Motion Master will send progress messages until the firmware installation is complete. * * A call to a request method will return an Observable of: (1) the corresponding status message, * for example a call to `getDeviceInfo` will return an instance of `MotionMasterMessage.Status.DeviceInfo`, * (2) request status - one of "succeeded," "failed," or "running.", and (3) request message id. * * If the request fails on Motion Master, the function will throw an error. It can also throw an error if the request times out. * * Request methods have an optional messageId input parameter. * If `messageId` is not provided, one will be generated before sending the request message to Motion Master. * Status messages (responses) received from Motion Master that correspond to the previous request will have the same `messageId` as the one in the request. * This is how we match requests with response messages in full-duplex asynchronous communication (WebSockets, ZeroMQ). * Matching request/response by message id is inspired by the [JSON-RPC 2.0 Specification](https://www.jsonrpc.org/specification). * * Almost all request methods have a mandatory `requestTimeout` input parameter. * This parameter specifies how long (in milliseconds) the client will wait for the status (response) messages corresponding to the previous request. * If the status message is not received in due time, the request method will throw a timeout error. * The error doesn't mean the request has failed on Motion Master, but rather that the client has given up waiting for the response(s). * It's possible to stop some ongoing procedures on Motion Master with the corresponding stop messages, for example, StopFullAutoTuning. * * @example * How to handle a request method timeout error: * ```typescript * req.getDeviceInfo(10).subscribe({ * next: (status) => console.log(status), * error: (err: unknown) => { * if (err instanceof TimeoutError) { * alert('Request has timed out'); * } * } * }); * ``` * * Request methods for a particular device, like `getDeviceParameterInfo`, accept the type of request message as the first input parameter as defined in the proto file. * For `getDeviceParameterInfo`, that's `MotionMasterMessage.Request.IGetDeviceParameterInfo`. This type is extended (via type intersection) by `DeviceRefObj`. * This is done in order to support multiple ways to reference a device. Motion Master only supports device addresses, which it re-generates for each device on power cycle. * Because device addresses can change, for scripts and applications, it's preferred to use a device reference that won't change. * The device serial number in the hardware description file uniquely identifies the device and doesn't change. This is what each request message is extended with. * Before sending the request message to Motion Master, the device address gets resolved and is set on the request message. * Besides the device address and device serial number, devices can be referenced by position (sequence number in the network chain). * * It is ensured that the Observable returned from a call to the request method will eventually complete, so a call to unsubscribe is not required. * The Observable will complete when the request status is either "succeeded" or "failed," or it will complete (error) due to a timeout. * Finding out if a request has completed, failed, or is still ongoing is different for each request - it depends on the status messages, see {@link requestStatusResolver}. * Request methods handle this and for each request, they will emit status messages with one of "succeeded," "failed," or "running" request statuses. * * Besides the request methods, this class contains many helper methods such as the ones for getting and setting device parameter values and * saving all parameters, which involves complex logic like multiple repeating requests to determine if saving all parameters has completed successfully. */ export declare class MotionMasterReqResClient { readonly socket: MotionMasterReqResSocket; /** * Maps a device address to a map of parameter ID to a type value key. * * @example * ```typescript * new Map([ * [2045285448, new Map([ * ["0x1018:02", { * id: '0x1018:02', * index: 4120, * subindex: 2, * name: 'Product Code', * unit: '', * group: 'Identity object', * readAccess: true, * writeAccess: false, * min: undefined, * max: undefined, * valueType: 7, // UNSIGNED32 * typeValueKey: "uintValue" * }] * ])] * ]); * ``` * * When setting a parameter value, only one of int, uint, float, string, or raw type value fields must be set. * This is defined in the proto file SetDeviceParameterValues request message. * * Device parameters have a richer set of base types defined in ESI, and they are provided by the DeviceParameterInfo status message. * When device parameter info is fetched, this map gets updated by mapping device parameter types to "oneof" proto types, e.g., `INTEGER32 -> intValue`. * * This map helps in simplifying the API by allowing users to set parameter values without specifying the type value field. * One can simply call `setParameterValue(2045285448, 0x2004, 0x03, 2500)`, and the correct type value field on the proto message will be set, `uintValue` in this example. */ readonly deviceParameterInfoMap: Map>; /** * A list of devices available on the network. * Each device entry specifies its type, position in the network, and address. * Additionally, it includes a parsed Integro variant and hardware description for each device. */ readonly devices: Device[]; readonly mmcidb: MotionMasterClientIndexedDB; constructor(socket: MotionMasterReqResSocket); /** * Clears the state of an instance of this class. * * This method is typically called when Motion Master is deinitializing or the socket is closing. * Both maps are implicitly populated when a device or parameter type value key gets resolved. */ clearDevicesInformation(): void; /** * Pings the system. * * The client must send messages to Motion Master at regular intervals for Motion Master to consider it alive. * When the client is considered "not alive", Motion Master will stop the ongoing procedures and monitorings started by that client. * Each client on the Motion Master side has its own default timeout, which can be changed by {@link setSystemClientTimeout}. */ pingSystem(messageId?: string): Observable; /** * Get the system version. * * Retrieve the version of Motion Master. The version follows [Semantic Versioning 2.0.0](https://semver.org/). */ getSystemVersion(requestTimeout: number, messageId?: string): Observable; /** * Retrieve system information from Motion Master. * * The returned information includes: * - `version`: The Motion Master version, following [Semantic Versioning 2.0.0](https://semver.org/). * - `startOptions`: The command-line arguments used to start Motion Master. */ getSystemInformation(requestTimeout: number, messageId?: string): Observable; /** * Get device info. * * Device info includes a list of devices on the network. Each device has a type, position in the network, and a device address. * At the time of writing, the device alias is not yet supported. * * Motion Master will assign a unique device address to each device in the list. * The device address is what the client libraries use to make requests like `getDeviceParameter` for a particular device. * The device address is only valid for the duration of the session, that is, until Motion Master re-initializes the devices, for example, * when devices are power cycled or the Motion Master process is restarted. */ getDeviceInfo(requestTimeout: number, messageId?: string): Observable; /** * Get device parameter info. * * Device parameter info includes a list of all parameters for the requested device, but without the parameter values. * Getting device parameter values can take more than 20ms per parameter using the IgH EtherCAT Master library. * Not all clients require all the parameter values at once, like OBLAC Drives, so this method is useful for getting * the list of available parameters and then separately obtaining the values of some required parameters. * * The returned list of device parameters will include some basic data for each parameter: index, subindex, * name, unit, group (ARRAY or RECORD name for subitems), read and write access, min and max, and value type. * Min and max values are not yet fully supported - they contain the min/max values for the used base type. * The same info and more can be read from the "SOMANET_CiA_402.xml" file, but getting info from the ESI file is more complicated. * It requires an XML parsing library and knowing how to read objects info from a dictionary and assigned modules. */ getDeviceParameterInfo(props: GetDeviceParameterInfoRequest, requestTimeout: number, messageId?: string): Observable; /** * Get device parameter values. * * As mentioned earlier, fetching parameter values can take 20ms or more. However, * it can also fail completely or timeout on the master side, registering as a "cannot refresh value" error. */ getDeviceParameterValues(props: GetDeviceParameterValuesRequest, requestTimeout: number, messageId?: string): Observable; /** * Get multi-device parameter values. * * Allows requesting parameter values from multiple devices at the same time. */ getMultiDeviceParameterValues(props: GetMultiDeviceParameterValuesRequest, requestTimeout: number, messageId?: string): Observable; /** * Set device parameter values. */ setDeviceParameterValues(props: SetDeviceParameterValuesRequest, requestTimeout: number, messageId?: string): Observable; /** * Set multi-device parameter values. * * Allows setting parameter values on multiple devices at the same time. */ setMultiDeviceParameterValues(props: SetMultiDeviceParameterValuesRequest, requestTimeout: number, messageId?: string): Observable; /** * Get device file list. * * Motion Master will use Filetransfer over EtherCAT (FoE) to obtain the list of files from a device. * There isn't an actual command for getting the list, but rather the content of a specially named file "fs-getlist" is the file list. * The list can be read like any other file from a device using the IgH EtherCAT Master for Linux CLI program: * * ``` * $ ethercat foe_read fs-getlist * ``` * * At the time of writing this document, "fs-getlist" can return a maximum of 32 files (subject to change) in the list. This is a firmware limitation. * However, more than 32 files can be stored on the device flash memory, but they won't appear in the list. * Also, note that FoE can behave differently in the bootstrap firmware, which runs in the BOOT EtherCAT state, and * SOMANET firmware, which runs in other EtherCAT states like PREOP/OP. Bootstrap tends to be buggier since it cannot be updated easily, so * Motion Master has certain workarounds to overcome these FoE differences and bugs. */ getDeviceFileList(props: GetDeviceFileListRequest, requestTimeout: number, messageId?: string): Observable; /** * Get device file. * * Motion Master uses Filetransfer over EtherCAT (FoE) to read and send back the content of a file from the device flash memory. * * The IgH EtherCAT Master library used by Motion Master limits the file read buffer to 9KB, so any file written to flash that is larger than 9KB * needs to be split into parts of max 9KB. Motion Master does this automatically on request to {@link setDeviceFile}. * * Upon receiving this request, Motion Master will first read the list of files on a device, see {@link getDeviceFileList}. * It does that in order to determine if the requested file, for example, "SOMANET_CiA_402.xml," has been stored in multiple parts. * The parts are named like "SOMANET_CiA_402.xml.zip.part000," "SOMANET_CiA_402.xml.zip.part001," and so on. * Motion Master will read all parts of the requested file, unzip it, and send the content back to a client. * Since the number of items in the list of files is limited to 32 (based on the firmware version), Motion Master might not see the file, * but in any case, it will try to read the content of it. * If the file exists, it will return its content; otherwise, it will return the file not found error. * * Zipped files will be automatically unzipped, and their content returned; for example, "stack_image.svg.zip" can be stored * in one or multiple files depending on the size. No matter how it's stored, it will be unzipped, and its content returned as * text (SVG) instead of zipped content (binary). * * In BOOT EtherCAT state, it's only allowed to read the .hardware_description file. This was done because * the bootloader firmware would hang when trying to read a corrupted or missing file. * * If the requested file content is empty, Motion Master will return a not found error. This is subject to change now that Motion Master reads the file error codes. * * SOMANET_CiA_402.xml and SOMANET_CiA_402.xml.zip files are stored in IndexedDB for faster access. */ getDeviceFile(props: GetDeviceFileRequest, requestTimeout: number, messageId?: string): Observable; private getDeviceFileUsingResolvedDeviceAddress; /** * Fixing a production screw-up that affects a very important customer. Added on February 29th, 2024. * In addition to addressing the production issue, this function will return a default `.hardware_description` file * if it cannot be found on the device and `stack_info.json` is also missing. */ protected fixProductionScrewUp(status: DeviceFileStatus): Promise; /** * Set device file. * * Motion Master uses Filetransfer over EtherCAT (FoE) to write files to the device flash memory. * * The IgH EtherCAT Master library used by Motion Master limits the file read buffer to 9KB, so any file written to flash that is larger than 9KB * needs to be split into parts of max 9KB. Motion Master does this automatically by first zipping the content and then writing the parts. * The parts are named in the following manner: "SOMANET_CiA_402.xml.zip.part000," "SOMANET_CiA_402.xml.zip.part001," and so on. */ setDeviceFile(props: SetDeviceFileRequest, requestTimeout: number, messageId?: string): Observable; /** * Delete device file. * * Motion Master uses Filetransfer over EtherCAT (FoE) to delete files from the device flash memory. * * If the file to delete is written in parts, Motion Master will ensure that all parts are deleted. * It does this by reading the list of files on a device, see {@link getDeviceFileList}, removing all parts from that list, and then * re-reading the list again to ensure that there are no leftovers if there were more than 32 files in the list. If there are still * more than 32 files in the list, Motion Master will blindly try to make sure there are no file parts left in the memory (may or may not work). */ deleteDeviceFile(props: DeleteDeviceFileRequest, requestTimeout: number, messageId?: string): Observable; /** * Reset device fault. * * When an error occurs on a device, the device will go into the Fault reaction active state (transition 13) and then automatically to the Fault state (transition 14). * The CiA402 state of a device can be derived from the value of the Statusword object (0x6041:00). * In order to exit the Fault state and enter the Switch on disabled state (transition 15), the master must send a Fault reset command via the Controlword object (0x6040:00). * * When this request is sent to Motion Master, it will attempt to reset the fault. Resetting the fault can either succeed or fail. * While resetting the fault, Motion Master will use the current Controlword value and set the Reset fault bit to 1. * However, upon completion, whether successful or encountering an error, Motion Master will set it back to 0. * * Motion Master will return a "No Fault" warning when this request is sent, and the device is not in the Fault or Fault reaction active state. * If this request is sent when the device is in the Fault reaction active state, Motion Master will * wait for the automatic transition (14) to the Fault state before attempting to reset the fault. * When Motion Master sets the Controlword Fault bit to 1, it will also periodically check if the device is no longer in the Fault state. * After a few seconds, if the device is still in the Fault state, Motion Master will give up and return a timeout error. */ resetDeviceFault(props: ResetDeviceFaultRequest, requestTimeout: number, messageId?: string): Observable; /** * Stop device. * * Motion Master will use the current value of the Controlword object and set the command on it to Quick stop. * It will then wait for up to 2 seconds for a device to enter one of the following CiA402 states: Switch on disabled, Operation enabled, Fault. * This is achieved by periodically checking the value of the Statusword object. If the device fails to enter one of those states within the specified time, * Motion Master will return a timeout or a quick stop failed error. */ stopDevice(props: StopDeviceRequest, requestTimeout: number, messageId?: string): Observable; /** * Start device firmware installation. * * When Motion Master receives this request for a device, it will perform the following steps: * - Switch the device to the BOOT EtherCAT state; the device will then run the bootloader instead of the firmware. * - Validate the firmware package. * - Delete files found in the package from the device flash memory (SOMANET_CiA_402.xml and stack_image.svg). * - Write files other than the firmware binaries and SII from the package to the device (SOMANET_CiA_402.xml and stack_image.svg). * - (Optional) Install the SII file using the IgH EtherCAT Master library write SII function, or SOEM EEPROM tool. * - Write the firmware binaries to the device using predefined names like app_firmware.bin and com_firmware.bin. * * During the firmware installation, Motion Master will send progress messages back to clients. * If Motion Master encounters a failure in any step other than SII write, it will send an error. If SII write fails, only a warning will be sent. */ startDeviceFirmwareInstallation(props: StartDeviceFirmwareInstallationRequest, requestTimeout: number, messageId?: string): Observable; /** * Extracts the ESI file (SOMANET_CiA_402.xml) from a firmware package and stores its unzipped content in * IndexedDB, keyed by the given firmware version. * * This is the install-time counterpart to the read-time caching in {@link getDeviceFile}: once the ESI is * cached here, OBLAC can resolve it from IndexedDB without reading it back from the drive. This is what * allows the ESI file (SOMANET_CiA_402.xml.zip) to be skipped during firmware installation, which avoids * slow and unreliable FoE transfers and works around devices (e.g. NetX) that reject writing that file. * * It is a no-op when run outside the browser, when IndexedDB is unavailable, or when the package does not * contain an ESI file (for example, an empty firmware package). * * @param firmwareVersion - The firmware version to key the ESI by; this must match the value reported by the * device parameter 0x100a:00 after installation, which {@link getDeviceFile} uses. * @param firmwarePackageContent - The firmware package ZIP archive content. * @returns `true` if an ESI was extracted and stored, `false` if it was a no-op (no IndexedDB or no ESI). */ cacheEsiFromFirmwarePackage(firmwareVersion: string, firmwarePackageContent: Uint8Array): Promise; /** * Installs a firmware package while keeping ESI handling local, by wrapping {@link startDeviceFirmwareInstallation} * without changing its behavior. Compared to a plain installation, this: * - Defaults to skipping the ESI file (SOMANET_CiA_402.xml.zip) so it is not written to the drive, which avoids * slow and unreliable FoE transfers and works around devices (e.g. NetX) that reject writing that file. This is * user-overridable: when `props.skipFiles` is provided it is passed through unchanged, so a caller can choose to * still write the ESI by omitting it from that list. * - Extracts the ESI from the package and stores it in IndexedDB keyed by firmware version (see * {@link cacheEsiFromFirmwarePackage}) *before* the installation starts, so it can be resolved locally by * {@link getDeviceFile}. It must be cached up front because, with the ESI skipped on the drive, Motion Master * will try to read it back right after installation. This caching happens regardless of whether the ESI is * also written to the drive. A caching failure is logged but does not prevent installation. * * @param firmwareVersion - The firmware version to key the cached ESI by; this must match the value reported by * the device parameter 0x100a:00 after installation, which {@link getDeviceFile} uses. * For OBLAC firmware packages this is the version encoded in the package filename, see * {@link extractFirmwareVersionFromFirmwarePackageFilename}. When it cannot be determined * (e.g. an arbitrary package with an unrecognized filename), pass an empty value to skip * caching; the read path then falls back to the online source. */ installFirmwareAndCacheEsi(firmwareVersion: string | undefined, props: StartDeviceFirmwareInstallationRequest, requestTimeout: number, messageId?: string): Observable; /** * Get device log. * * The device log is stored in two files due to the IgH EtherCAT Master library 9KB file size limitation, as explained in {@link getDeviceFile}. * The device automatically writes the log to logging_curr.log and copies that file to logging_prev.log once it reaches 9KB. * When Motion Master receives this request, it will read both of these files and return their combined contents. */ getDeviceLog(props: GetDeviceLogRequest, requestTimeout: number, messageId?: string): Observable; /** * Start cogging torque recording. * * Cogging torque compensation (CTC) recording can be initiated with or without auto-config. * In the proto file, skipping the auto-config is currently named skip_auto_tuning. The field name is deprecated and will be renamed. * * If CTC recording is started without auto-config, users must ensure that the encoder on the motor shaft is used for all functions: commutation, position, and velocity. * If this is not the case, Motion Master will return an invalid encoder configuration error. * Recording can also fail if the position controller is not tuned. * * If CTC recording is started with auto-config, Motion Master will: * - Change the encoder configuration to have all encoder functions on the motor shaft. * - Disable CTC. * - Change the velocity feed forward value. * - Change the position and velocity filter types and cutoff frequencies. * - Run iterative sharpening position controller auto-tuning to compute the optimal PID values (gains) for CTC recording. * * All parameter values that Motion Master changes as part of the auto-config are first stored in memory and once the CTC recording is done, they are reverted back. * * CTC recording is initiated by changing the Modes of operation (0x6060) parameter value to -1 (Cogging compensation recording mode). * During the operation, Motion Master will monitor the Cogging torque compensation state parameter (0x2008:01) to know when the recording is in progress and when it's done. * * The result of CTC recording is the cogging_torque.bin file written to the device flash memory. The size of this file is 2048 bytes. * Each pair of bytes represents a 16-bit signed integer value in mNm (millinewton-meter). * * This request will turn the motor. */ startCoggingTorqueRecording(props: StartCoggingTorqueRecordingRequest, requestTimeout: number, messageId?: string): Observable; /** * Get cogging torque data. * * The cogging_torque.bin file is the result of cogging torque compensation recording, as explained in {@link startCoggingTorqueRecording}. * The size of this file is 2048 bytes, where each pair of bytes represents a 16-bit signed integer value in mNm (millinewton-meter). * * Motion Master will read the cogging_torque.bin file, convert the bytes to 16-bit signed integer values, and return them as an array of numbers. */ getCoggingTorqueData(props: GetCoggingTorqueDataRequest, requestTimeout: number, messageId?: string): Observable; /** * Start offset detection. * * Running offset detection differs for firmwares =v5. * * For devices running firmware >=v5, Motion Master will execute multiple OS commands. * Before initiating any command, the device is switched to Modes of operation -2 (Diagnostics mode), and * it's put into the operation-enabled CiA402 state. The OS commands are then executed in the following order: * - Open phase detection * - Phase resistance measurement * - Phase inductance measurement * - Pole pair detection * - Motor phase order detection * - Commutation offset measurement * * Motion Master will return an error if any of the following OS commands fail: open phase detection, * phase order detection, commutation offset measurement. * If other OS commands fail, Motion Master will continue with the procedure and only return a warning. * * Once the commutation offset measurement command completes, it will update the following parameter values: * - 0x2001:00 Commutation angle offset to the computed offset value * - 0x2009:01 Commutation offset State to 2 (OFFSET_VALID) * - 0x2003:05 Motor phases inverted will be changed by the firmware * * For devices running firmware <5, the same Modes of operation -2 is used, but it's named Commutation offset detection mode, * and it will run as a single procedure as soon as the device is switched to CiA402 operation-enabled state. * The end result is the same; the procedure will update 0x2001:00 and 0x2009:01 parameter values. * * This request will turn the motor. */ startOffsetDetection(props: StartOffsetDetectionRequest, requestTimeout: number, messageId?: string): Observable; /** * @deprecated use {@link startSystemIdentification} instead */ startPlantIdentification(props: StartPlantModelIdentificationRequest & DeviceRefObj, requestTimeout: number, messageId?: string): Observable; /** * Compute auto-tuning gains. * * Auto-tuning gains can be computed for the position or the velocity controller. * * The prerequisites for running this procedure are a configured motor and the existence of * the plant_model.csv file created by previously running the system identification {@link startSystemIdentification}. * Motion Master will return an error if the plant_model.csv file is not found. * * In OBLAC Drives, this request is called when the tuning sliders (damping ratio, bandwidth) are moved and * during the CTC recording {@link startCoggingTorqueRecording} when auto-config is not skipped. * * Motion Master will compute the PID gains using a proprietary algorithm and update the Kp, Ki, Kd values of the 0x2011 and 0x2012 parameters. */ computeAutoTuningGains(props: ComputeAutoTuningGainsRequest, requestTimeout: number, messageId?: string): Observable; /** * Set motion controller parameters. * * This request sets the target value for a device on Motion Master. * * A previous call to {@link enableMotionController} will set the mode of operation to CSP, CSV, or CST and optionally enable filtering. */ setMotionControllerParameters(props: SetMotionControllerParametersRequest, messageId?: string): Observable; /** * Enable motion controller. * * This request will set the mode of operation to CSP, CSV, or CST and optionally enable filtering. * * If filtering is enabled, Motion Master will compute an intermediate target value in each cycle, and depending on the active mode of operation, * set the value of one of 0x607A Target position, 0x60FF Target velocity, 0x6071 Target torque to that value. * * The target value can be updated with {@link setMotionControllerParameters}. */ enableMotionController(props: EnableMotionControllerRequest, requestTimeout: number, messageId?: string): Observable; /** * Disable motion controller. * * Depending on the current CiA402 state, this request will do the following: * - If the device is in Quick stop active, it will transition to Switch on disabled state. * - If the device is in Operation enabled, it will transition to Switched on state. */ disableMotionController(props: MotionMasterMessage.Request.IDisableMotionController & DeviceRefObj, requestTimeout: number, messageId?: string): Observable; /** * Set signal generator parameters. * * This request will update the signal generator parameter values for a device on Motion Master. * The selected signal generator is then started by {@link startSignalGenerator}. * The signal generator must be started within the next 60 seconds before Motion Master invalidates the previously set parameters. */ setSignalGeneratorParameters(props: SetSignalGeneratorParametersRequest, requestTimeout: number, messageId?: string): Observable; /** * Start signal generator. * * This request will start one of the signal generators based on the * previously set parameters with {@link setSignalGeneratorParameters}. * * Signal generators are started by changing the mode of operation, putting the device into Operation enabled CiA402 state, * and setting the target value. The mode of operation set depends on the type of signal generator and the selected controller: * - For the simple & advanced step response and the sine wave, one of CSP, CSV, or CST is set. * - For the ramp, trapezoidal, and bidirectional signal generators, also called profiles, one of the PP, PV, TQ is set. * * Currently, the only profile type that the firmware supports is the ramp profile. * Motion Master uses this profile type to construct and run the following signals: ramp, trapezoidal, and bidirectional. * Sine wave is also a profile, but it is currently being generated on Motion Master alone. * Firmwares >=5.2 will support generating and running sine wave profiles on devices themselves. This will enable lossless profile * execution on possibly higher frequencies. Future Motion Master versions will switch to this method. * * For the simple step response, Motion Master will only set the target value, wait for the specified holding duration, * and then send a Quick Stop command. * * The advanced step response is similar to the simple one, but, after the holding duration, it will set the new target * multiple times depending on the shape, and then send a Quick Stop if the repeat option is set to NO. If repeat is set to YES, * then the signal generator will run indefinitely, and the users must stop it manually. * * Before running a profile, Motion Master will check if the device supports the profile modes by looking at 0x6502 Supported drive modes. * If profile modes are not supported, then the profiles will be generated on Motion Master. This means the targets will be computed upfront. * If profiles are supported, then the ramp, trapezoidal, and bidirectional signal generators are run in profile mode of operation. * To prepare the signal generator for execution, Motion Master will set the following parameters: * - 0x6081:00 Profile velocity (only for the position controller) * - 0x6083:00 Profile acceleration * - 0x6084:00 Profile deceleration * Motion Master knows when the profile has completed by comparing the demand with the actual value, taking into account the * holding duration and the shape of the profile. Once the profile is considered complete, Motion Master will send a Quick Stop, but * only if repeat is set to NO. * * The sine wave profile is generated upfront on Motion Master. Targets are computed for each master cycle (millisecond). * Once the last computed target has been set, Motion Master will send a Quick Stop if repeat is set to NO. * * For all signal generators, Motion Master will check the requested target against the currently set software position limits * and, if necessary, alter it while returning a warning. * * This request will turn the motor. */ startSignalGenerator(props: MotionMasterMessage.Request.IStartSignalGenerator & DeviceRefObj, requestTimeout: number, messageId?: string): Observable; /** * Stop signal generator. * * This request will send a Quick Stop command to the device. */ stopSignalGenerator(props: StopSignalGeneratorRequest, requestTimeout: number, messageId?: string): Observable; /** * Start monitoring device parameter values. * * When monitoring is started, Motion Master will begin and continue reading values from the device * and send them back to a client at the specified interval on the given topic. * * The request is made through the req/res socket {@link MotionMasterReqResSocket}, * but the status messages will arrive on the pub/sub socket {@link MotionMasterPubSubSocket}. * * The same monitoring can read both PDO and SDO values. PDO values will be updated on every Motion Master cycle (1ms). * How fast SDO values will update depends on the number of SDOs being monitored. Motion Master reads the SDO values in a sequence, * so, for example, if there are 10 SDOs and it takes 20ms to read a single SDO, it will take approximately 200ms for each SDO to get updated. * IgH EtherCAT Master supports non-blocking SDO reading with a request to read and check the state of the request (one of not used, busy, failed, succeeded). * A future version of Motion Master will likely leverage this and update SDO values out of order as each of the requests to update SDO succeeds. * This should decrease the time it takes to read multiple SDOs. * If a parameter is required to be updated more frequently, it should be mapped as a PDO. * * Firmware versions >=5.2 support SDO complete access, but it is currently not being supported in Motion Master. * With SDO complete access, RECORD and ARRAY subitems can be read with a single request. * * The interval is given in microseconds. * * The topic should be unique. The previous monitoring will stop if the given topic is reused. * Clients can easily stop one another's monitoring by using the same topic. * Prefixing topics with the client id or some other unique identifier is suggested. * * When the monitoring request is received, Motion Master will mark all requested parameters as stale. * The first time a parameter gets refreshed from a device, it'll be marked as not stale. * Motion Master won't start publishing parameter values until all parameters are marked as not stale. * This was done to satisfy the firmware test client applications. * * Stopping the ongoing monitoring is done through the req/res socket using * the request message ID of the initial start monitoring message {@link stopMonitoringDeviceParameterValues}. */ startMonitoringDeviceParameterValues(props: StartMonitoringDeviceParameterValuesRequest, requestTimeout: number, messageId?: string): Observable; /** * Stop monitoring device parameter values. * * The Message ID used for {@link startMonitoringDeviceParameterValues} uniquely identifies a monitoring and is used for stopping it. */ stopMonitoringDeviceParameterValues(props: StopMonitoringDeviceParameterValuesRequest, messageId?: string): Observable; /** * Get the EtherCAT network state. * * Returns one of the EtherCAT network states: BOOT, INIT, PRE-OP, SAFE-OP, OP. * The state is returned as an enum value: INIT: 1, PREOP: 2, BOOT: 3, SAFEOP: 4, OP: 5. */ getEthercatNetworkState(props: GetEthercatNetworkStateRequest, requestTimeout: number, messageId?: string): Observable; /** * Set the EtherCAT network state. * * Set the EtherCAT network state to one of: BOOT, INIT, PRE-OP, SAFE-OP, OP. * The state is set by an enum value: INIT: 1, PREOP: 2, BOOT: 3, SAFEOP: 4, OP: 5. * * When switching from PRE-OP to OP, MM will reinitialize slaves to update the PDO mapping. */ setEthercatNetworkState(props: SetEthercatNetworkStateRequest, requestTimeout: number, messageId?: string): Observable; /** * @deprecated use {@link startCirculoEncoderNarrowAngleCalibrationProcedure} instead */ startNarrowAngleCalibration(props: StartNarrowAngleCalibrationRequest, requestTimeout: number, messageId?: string): Observable; /** * Set system client timeout. * * This request will update the client timeout. * * The client timeout specifies how long Motion Master will wait for the client to send a ping or any other message before * considering it gone and clearing the resources (stopping procedures and monitorings) related to that client. * * The default client timeout is 1000ms. * * Clients will typically change this once the socket connection is established. */ setSystemClientTimeout(props: SetSystemClientTimeoutRequest, messageId?: string): Observable; /** * Start system identification. * * This request will run the system identification procedure, which identifies the plant model. * * Pre-conditions: a configured motor and configured encoders. * * The chirp signal that the procedure generates only uses the torque controller. * The chirp signal is generated on Motion Master, and then, on every master cycle (1ms), the target torque value is set on a device. * Motion Master will send a Quick Stop to a device after the last target value is set. * * The request can fail for multiple reasons: the device is in the fault state, cannot set the op mode state, * or the system identification fails because not enough data points have been collected. * While running the chirp signal, the data points are collected, but due to potential communication lag, it can happen * that the master doesn't collect enough data points. If more than 80% of data points are missing, the procedure will fail. * If between 20%-80% of data points are missing, only a warning will be returned. The exact thresholds are subject to change. * * Before computing the plant model data based on the collected data points, Motion Master will interpolate the missing data points. * Plant model data is then computed and written to the plant_model.csv file on the device flash memory. * The plant model file is later used to compute the PID values using {@link computeAutoTuningGains} and {@link startFullAutoTuning}. * It's also used indirectly in {@link startCoggingTorqueRecording} when auto-config is turned on. * Motion Master will also update the integral limit values in 0x2011: Velocity controller and 0x2012: Position controller during this procedure. * * In future versions of the firmware, the chirp signal would be executed on the devices themselves, so no data points will be missing, * and the system identification will be able to run at higher frequencies and with higher precision. * * This request will turn the motor. */ startSystemIdentification(props: StartSystemIdentificationRequest, requestTimeout: number, messageId?: string): Observable; /** * Get Circulo encoder magnet distance. * * This feature is only available for firmwares >=v5. For older firmwares, Motion Master will return an error. * * Motion Master will read registers 0x2B and 0x2F on the specified encoder (by encoder ordinal), and then it will compute the magnet distance. * The computation depends on the Circulo type, encoder port, and ring revision. */ getCirculoEncoderMagnetDistance(props: MotionMasterMessage.Request.IGetCirculoEncoderMagnetDistance & DeviceRefObj, requestTimeout: number, messageId?: string): Observable; /** * Start the Circulo encoder narrow-angle calibration procedure. * * This feature is only available on firmwares >=v5. * * Before starting the procedure, Motion Master will check and return an error if: * - the firmware version is not >=v5 * - software position limits are set so that the required motor rotation is not possible * - for SMM devices, the encoder source type is not set to None * - the velocity resolution determined by the gear ratio, SI unit velocity, and feed constant is not high enough * * Before starting the procedure, Motion Master will do the following: * - send OS command 14 (Ignore BiSS status bits) so that no firmware warnings or errors are raised during the procedure. * - set certain encoder registers to their default values. * - set the BiSS encoder to raw mode. * - change the values of some device parameters: profile acceleration, deceleration, max motor speed, etc. * * The parameter values Motion Master sets depend on the type of the device (fetched from the hardware description file). * Once the operation has completed, Motion Master will roll back all of the above parameters to their initial values. * * Procedure: * - The procedure is run in velocity profile mode of operation. * - The procedure will do multiple iterations until the encoder data is satisfactory. * - The procedure can fail for various reasons: data out of range, motor too slow, bad data, internal error, etc. * - The procedure will run a maximum of 13 calibration iterations, up to 2 mins in total. * - One iteration turns the motor in one direction, and then the next one reverses the direction. * - Each iteration will record encoder data into HRD files (4kHz) that contain the raw data from the specified encoder. * - Motion Master will remove previous high-resolution data (HRD) files after each iteration. HRD streaming is configured/started using OS commands. * - After each iteration, which lasts ~6 seconds, the recorded data in HRD files is read and passed to the iC House library. * - The recorded data is sliced into 32-bit pairs of values of master and nonius track data. Motion Master creates two arrays out of this data and * passes that to the iC House library which computes the new calibration parameters depending on encoder type sine and cosine offset, gain, etc. * - The iterations are being repeated until the encoder (raw) data satisfies a certain threshold. * * The result of a successful calibration is setting multiple parameters into registers of the specified encoder. * * At the end of the procedure Motion Master will rotate the motor back to the starting position and run commutation offset detection. * There will also be a final iteration that only measures the values of a (now) calibrated encoder for display. * * Every progress status carries `maxPermissiblePhaseError`, the limit the calibration library measures the ring * against. Motion Master 5.8.3 and later report it. An older Motion Master reports 0, and this method fills in * the limit derived from the product and the external encoder type instead. That limit is only right for the * Circulo 7 and Circulo 9 rings. Score a progress status with `computeCirculoEncoderCalibrationProgressResult`. * * This request will turn the motor. */ startCirculoEncoderNarrowAngleCalibrationProcedure(props: StartCirculoEncoderNarrowAngleCalibrationProcedureRequest, requestTimeout: number, messageId?: string): Observable; /** * Get device CiA402 state. */ getDeviceCia402State(props: GetDeviceCiA402StateRequest, requestTimeout: number, messageId?: string): Observable; /** * Set device CiA402 state. */ setDeviceCia402State(props: SetDeviceCiA402StateRequest, requestTimeout: number, messageId?: string): Observable; /** * Get system log. * * The system log represents the collected standard output from the Motion Master process. * * This request will return the entire system log, which can be a maximum of approximately 2MB. * * The log level can be set as an environmental variable when the Motion Master process is started. * The log level can be selected in the OBLAC Drives Update Service expert mode before installing a release. * The supported log levels are: * - 6: Request content * - 5: Request type * - 4: Parameter value * - 3: Monitoring * - 2: Verbose 2 * - 1: Verbose 1 * - 0: Info * - 1: Warnings * - 2: Errors * - 3: Fatal errors */ getSystemLog(requestTimeout: number, messageId?: string): Observable; /** * Start device SII restore. * * This request uses the EEPROM tool from SOEM to overwrite the SII portion of the EEPROM on a device. * * Motion Master will verify the provided SII file before writing it to EEPROM. It will: * - Check the file content length, * - Compute CRC from a part of the SII file content and compare it to the CRC inside the file, * - Check the SII category types in the category header. * * Unlike IgH EtherCAT Master, which identifies interfaces by MAC address, the SOEM tool requires an adapter name. * Before calling the SOEM tool, Motion Master will find the adapter name by looking into /sys/class/net. * * The SOEM tool binary is delivered as a part of the Motion Master Docker image. */ startDeviceSiiRestore(props: StartDeviceSiiRestoreRequest, requestTimeout: number, messageId?: string): Observable; /** * Start open-loop field control. * * The precondition for running the open-loop field control is to have a configured motor. * No encoder configuration or offset detection is required. * * Open-loop field control is started by changing the Modes of operation (0x6060) parameter value to -3 (Open-loop field mode) and * setting the CiA402 state to Ready to switch on. * After that, Motion Master will run several OS commands that configure the open-loop field control parameters: * - Start angle [milliradian] * - End angle [milliradian] * - Max rotational speed [radian/s] * - Rotational acceleration [radian/s^2] * - Start length [permille of rated torque] * - End length [permille of rated torque] * - Length speed [permille of rated torque] * * After the configuration, Motion Master will switch the device to Operation enabled CiA402 state, and the profile will start. * * While the open-loop field control is running, Motion Master will monitor the target reached bit in the statusword. * When the target reached bit becomes 1, Motion Master will stop the procedure by changing the CiA402 state to Switched on. * * Motion Master will return an error if the device goes out of the Operation enabled state before the target reached bit becomes 1. * There is no timeout on the Motion Master side. * * This request will turn the motor. */ startOpenLoopFieldControl(props: StartOpenLoopFieldControlRequest, requestTimeout: number, messageId?: string): Observable; /** * @deprecated use {@link startFullAutoTuning} instead */ computeFullAutoTuningGains(props: ComputeFullAutoTuningGainsRequest, requestTimeout: number, messageId?: string): Observable; /** * Start full auto-tuning. * * The preconditions for running the full auto-tuning are a properly configured motor, brake, and encoders, * and having executed the offset detection and the system identification procedures. * * In order to successfully run the full auto-tuning procedure, the motor must not rotate, and the device must not be in CiA402 Operation enabled. * * Motion Master will try to read the plant_model.csv file, and if it doesn't exist, it will return an error. * * Before the operation starts, Motion Master will measure the actual velocity for 500ms at a standstill to determine the encoder noise. * The noise is then sent, along with some other parameters (velocity feedback filter, feed forward, DC link voltage, firmware version, and similar) * and data to a proprietary computation algorithm. * ADC current ratio, which is used in the computation script, is determined by the firmware version and the device hardware ID (e.g., 9500, 9501, 8501...). * * Full auto-tuning will compute the PID gains, and Motion Master will update the parameter values in the velocity or position controller, depending on the request. * * Motion Master will return the damping ratio, settling time, and bandwidth values when the procedure completes. UI will use these values to update the sliders in the Tuning screen. * * This procedure can be stopped with {@link stopFullAutoTuning}. */ startFullAutoTuning(props: StartFullAutoTuningRequest, requestTimeout: number, messageId?: string): Observable; /** * Stop full auto-tuning. * * Motion Master has only one exit point for this procedure, which is after the computation algorithm ends. * This means that, once stopped, the procedure will compute the gains, but Motion Master will not update the controller parameters. * A previously started full auto-tuning request will complete with an aborted error. */ stopFullAutoTuning(props: StopFullAutoTuningRequest, requestTimeout: number, messageId?: string): Observable; /** * Start Circulo encoder configuration. * * The preconditions for this procedure are to have a Circulo device with internal encoders and firmware >=v5. * * This procedure will set various internal encoder registers based on the hardware description, Circulo device type, and the encoder ordinal. * * Before updating the registers, Motion Master will send an OS command to ignore the BiSS status bits. * Once the procedure is done, the value of this register will be reverted. * * Depending on the setup, this procedure can take up to 30 seconds. * * This procedure can fail if it's already running, if it's not supported because of the firmware version, * or if the hardware description file is missing. * * While this procedure runs, Motion Master will report its progress. */ startCirculoEncoderConfiguration(props: StartCirculoEncoderConfigurationRequest, requestTimeout: number, messageId?: string): Observable; /** * @deprecated use {@link stopDevice} instead */ stopCirculoEncoderNarrowAngleCalibrationProcedure(props: StopCirculoEncoderNarrowAngleCalibrationProcedureRequest, requestTimeout: number, messageId?: string): Observable; /** * Start OS command. * * This request will execute an OS command and return the result as a byte array. * * Motion Master will check if an OS command is already running and use a mutex to ensure only one OS command runs at a time. * * This request can fail if the requested OS command is not supported. * * Motion Master will check if the OS command has failed and return an error. * * The OS command can timeout if it takes longer than the provided timeout in milliseconds, in which case Motion Master will return an error. */ startOsCommand(props: StartOsCommandRequest, requestTimeout: number, messageId?: string): Observable; /** * Execute the forward call request. * * This request is used to execute any function provided by the Standalone Auto-tuning Service which is started by the Motion Master. */ executeForwardCall(props: ExecuteForwardCallRequest, requestTimeout: number, messageId?: string): Observable; /** * Set PDO mode. */ setPdoMode(props: SetPdoModeRequest, requestTimeout: number, messageId?: string): Observable; /** * Send request. * * Create a Motion Master message with the provided request, optionally generate a unique message ID, * and then send the message through the socket. * * @returns the message ID */ sendRequest(request: MotionMasterMessage.IRequest, messageId?: string): string; /** * Get device SII. */ getDeviceSii(props: GetDeviceSiiRequest, requestTimeout: number, messageId?: string): Observable; /** * Get the device serial number by device address. * * This function does not make any requests; instead, it utilizes the previously mapped device serial number to an instance of a device. */ getSerialNumberByDeviceAddress(deviceAddress: number): string | undefined; /** * Resolve a device. * * Resolves the device object by its reference, which can be a position, serial number, or device address. * * This function will make requests to retrieve the list of devices and the .hardware_description file for each device, * but only if it has not been previously retrieved for this session. * * @throws errors if the device reference is invalid */ resolveDevice(deviceRef: DeviceRef | DeviceRefObj, requestTimeout?: number): Observable; /** * Resolve device address. * * This method should return the device address by a device reference object, * or throw an error if the device address cannot be found. * * Refer to the description of this class for more information. */ resolveDeviceAddress(deviceRef: DeviceRef | DeviceRefObj, requestTimeout?: number): Observable; /** * Get devices. * * Retrieve device information from Motion Master. * * For each device, it reads and parses the `.hardware_description` and `.variant` files, then assigns the data to the device object. */ getDevices(requestTimeout?: number): Observable; getParameterValue(deviceParameterId: string, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Observable; getParameterValue(deviceRef: DeviceRef, index: number, subindex: number, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Observable; upload(deviceParameterId: string, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Promise; upload(deviceRef: DeviceRef, index: number, subindex: number, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Promise; private createGetParameterValueObservable; private resolveGetDeviceParameterValueArguments; getParameterValues(ids: DeviceParameterIds, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Observable; uploadMany(ids: DeviceParameterIds, loadFromCache?: boolean, requestTimeout?: number, messageId?: string): Promise; resolveGetParameterValuesIds(ids: DeviceParameterIds): Observable; setParameterValue(deviceParameterId: string, value: ParameterValueType, valueTypeKey?: keyof Required, requestTimeout?: number, messageId?: string): Observable; setParameterValue(deviceRef: DeviceRef, index: number, subindex: number, value: ParameterValueType, valueTypeKey?: keyof Required, requestTimeout?: number, messageId?: string): Observable; download(deviceParameterId: string, value: ParameterValueType, valueTypeKey?: keyof Required, requestTimeout?: number, messageId?: string): Promise; download(deviceRef: DeviceRef, index: number, subindex: number, value: ParameterValueType, valueTypeKey?: keyof Required, requestTimeout?: number, messageId?: string): Promise; private createSetParameterValueObservable; /** * Resolve set device parameter value arguments. */ private resolveSetDeviceParameterValueArguments; setParameterValues(ids: { [deviceParameterId: string]: ParameterValueType; } | DeviceParameterAddressValue[], requestTimeout?: number, messageId?: string): Observable; downloadMany(ids: { [deviceParameterId: string]: ParameterValueType; } | DeviceParameterAddressValue[], requestTimeout?: number, messageId?: string): Promise; resolveDeviceParameterTypeValueKey(deviceRefObj: DeviceRefObj, index: number, subindex: number, typeValueKey?: ParameterTypeValueKey): Observable; resolveDeviceParameterInfoMap(deviceRef: DeviceRef | DeviceRefObj, requestTimeout?: number): Observable>; /** * Retrieves and constructs device parameters with optional ESI (EtherCAT Slave Information) extensions. * * This method resolves the target device, optionally loads and parses an ESI XML file, * gathers device parameter metadata, and then fetches the actual parameter values. * Optionally includes progress updates during value retrieval. * * @param props - An object containing the following properties: * - `deviceId` or other identifying fields from `DeviceRefObj` to resolve the device. * - `loadFromCache` (optional): Whether read from the device or from the cache in Motion Master. * - `sendProgress` (optional): Whether to emit progress updates during parameter value retrieval. * - `extendWithEsi` (optional): If true, attempts to load and parse the ESI XML file to enrich parameters with metadata. * - `skipReadingValues` (optional): If true, skips reading parameter values and returns only the parameter structure * resolved from device info, optionally extended with ESI metadata. * @param requestTimeout - Timeout in milliseconds to apply to the device parameter info and value retrieval. Defaults to 30,000 ms. * * @returns An Observable emitting an object containing: * - `parameters`: An array of fully built `DeviceParameter` objects. * - `progress`: A percentage (0–100) representing retrieval progress if `sendProgress` is enabled, otherwise 100. * * @throws An error if device parameter values could not be retrieved or are empty. */ getDeviceParameters(props: { loadFromCache?: boolean; sendProgress?: boolean; extendWithEsi?: boolean; skipReadingValues?: boolean; } & DeviceRefObj, requestTimeout?: number): Observable<{ parameters: DeviceParameter[]; progress: number; }>; /** * Get list of files. */ getFiles(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Get file content. */ getFile(deviceRef: DeviceRef, name: string, requestTimeout?: number, messageId?: string): Observable; /** * Retrieves a file from the specified device and attempts to decode its content as a UTF-8 string. * * This method uses a strict decoder (`fatal: true`). If the file contains binary data * or invalid UTF-8 sequences, the operation will fail, allowing the caller to handle * the error (e.g., by falling back to a raw binary download). * * @param deviceRef - The reference object identifying the target device. * @param name - The name of the file to retrieve. * @param requestTimeout - The timeout for the request in milliseconds (default: 10000). * @param messageId - Optional ID for tracing the request. * @returns An Observable that emits the decoded string content of the file. * @throws {Error} If the file content is returned as undefined (file missing). * @throws {TypeError} If the file content is not valid UTF-8 text. */ getDecodedFile(deviceRef: DeviceRef, name: string, requestTimeout?: number, messageId?: string): Observable; /** * Retrieves the plant model data for a given device. * * Reads and parses the 'plant_model.csv' file associated with the device reference, * extracting numerator and denominator coefficients as arrays of numbers, * along with friction and inertia parameters. * * @param deviceRef - Reference to the device to retrieve the model from. * @param requestTimeout - Optional timeout in milliseconds for the request. Defaults to 10000 ms. * @param messageId - Optional message identifier for tracking or logging purposes. * @returns An Observable that emits the parsed PlantModel object or undefined if no content is available. */ getPlantModel(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Unlock protected files. * * This will enable the deletion of protected files. * Protected files begin with a period, such as '.hardware_description'. */ unlockProtectedFiles(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Set file content. */ setFile(deviceRef: DeviceRef, name: string, content: Uint8Array, overwrite?: boolean, requestTimeout?: number, messageId?: string): Observable; /** * Delete file. */ deleteFile(deviceRef: DeviceRef, name: string, requestTimeout?: number, messageId?: string): Observable; /** * Retrieve and parse the `.hardware_description` file. */ getHardwareDescription(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Retrieve and parse the `stack_info.json` file. */ getStackInfo(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Retrieve and parse the `.variant` file. */ getIntegroVariant(deviceRef: DeviceRef, requestTimeout?: number): Observable; /** * Get system log lines. * * Get the system log content and parse it into an array of lines, where each line contains the date, uptime, ID, file, level, and message. */ getSystemLogLines(requestTimeout?: number, messageId?: string): Observable; /** * Retrieves the UI configuration from the device's `ui.config.json` file. * * @param deviceRef - Reference to the target device from which to fetch the config. * @param requestTimeout - Optional timeout in milliseconds for the file retrieval request (default is 10,000 ms). * @param messageId - Optional message identifier for tracking or logging purposes. * @returns An Observable emitting the parsed `UiConfig` object from the device, or an empty object if the content is unavailable. */ getUiConfig(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Updates the UI configuration file `ui.config.json` on the device by writing the provided PDO mapping. * * This method retrieves the current UI configuration from the device, * updates its `pdoMapping` property with the provided mapping, * then serializes and writes the updated configuration back to the device file system. * * @param deviceRef - Reference to the target device containing the UI configuration file. * @param pdoMapping - The PDO mapping object to be saved within the UI configuration. * @returns An Observable that emits the status of the file write operation. */ writePdoMappingToUiConfigFile(deviceRef: DeviceRef, pdoMapping: UiPdoMapping): Observable; /** * Removes the PDO mapping from the UI configuration file `ui.config.json` on the device. * * This method fetches the existing UI configuration, deletes the `pdoMapping` property if present, * then writes the updated configuration back to the device. * * @param deviceRef - Reference to the target device containing the UI configuration file. * @returns An Observable that emits the status of the file write operation. */ removePdoMappingFromUiConfigFile(deviceRef: DeviceRef): Observable; /** * Store parameters. * * Command the device to store the parameters into config.csv, then delay initially and subsequently check if the value of * the Store parameters has changed to 1, indicating the successful completion. * * {@link https://www.synapticon.com/documentation/circulo/sw5.0/device_info/save_restore_config.html} */ storeParameters(deviceRef: DeviceRef, retryConfig?: RetryConfig): Observable; /** * Restore default parameters. * * Sends a command to the device to restore all default parameters (0x1011:01) or manufacturer default parameters (0x1011:04). * After setting the value to 0x64616f6c, the function briefly waits and checks if 0x1011:01 updates to 1, * confirming the restoration process has completed successfully. This check will retry a few times and will fail if the value doesn't revert to 1. * * For 0x1011:01, the configuration is loaded in the following order: first from the .factory_config file, * then from the config.csv file, and finally from the .assembly_config file, with values in the latter files overriding earlier ones. * * For 0x1011:04, the configuration is loaded from the .factory_config file, followed by the .assembly_config file, * with values in the latter overriding those in the former. * * Restoring default parameters will only override those stored in .factory_config, config.csv, and .assembly_config. * All other parameters, such as target values and PDO mappings, will remain unchanged. * * @throws Error if the device does not revert the value to 1 after the specified number of retries. * * For more information, refer to the documentation: * {@link https://www.synapticon.com/documentation/circulo/sw5.0/device_info/save_restore_config.html} */ restoreDefaultParameters(deviceRef: DeviceRef, type?: RestoreDefaultParametersType, retryConfig?: RetryConfig): Observable; /** * Match parameter value. * * This function will retrieve a parameter value from a device and compare it with the expected value. * * @throws Error if the values do not match. */ matchParameterValue(deviceRef: DeviceRef, index: number, subindex: number, expectedValue: number): Observable; matchCia402States(deviceRef: DeviceRef, expectedStates: Cia402State[]): Observable; /** * Helper function to enable motion. */ enableMotion(deviceRef: DeviceRef, controllerType: MotionMasterMessage.Request.EnableMotionController.ControllerType, filter?: boolean, requestTimeout?: number, messageId?: string): Observable; /** * A helper function to disable motion. */ disableMotion(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * A helper function to set the motion target. */ setMotionTarget(deviceRef: DeviceRef, target: number, messageId?: string): Observable; /** * A helper function to set the value of the Modes of Operation parameter (0x6060:00). */ setModesOfOperation(deviceRef: DeviceRef, modesOfOperation: ModesOfOperation): Observable; /** * Get CiA402 state. */ getCia402State(deviceRef: DeviceRef, requestTimeout?: number, messageId?: string): Observable; /** * Transition to CiA402 state. * * This function will utilize the current value of the controlword and modify it to transition to the requested CiA402 state. * * Only one transition will occur, except when the current CiA402 state is SWITCH_ON_DISABLED. In this case, * the first transition is from SOD to RTSO, and then from RTSO to the requested CiA402 state. * * The Statusword will be polled to check if the device has successfully transitioned to the requested CiA402 state. * When transitioning to QSA, the Statusword will be checked against both QSA and SOD. * This is necessary because the automatic transition from QSA to SOD can occur faster than the client's polling interval. */ transitionToCia402State(deviceRef: DeviceRef, targetState: Cia402State): Promise; /** * Prepares the homing procedure by updating the controlword on the specified device. * * This function performs the following actions: * 1. Clears the halt bit (bit 8) by setting it to 0. * 2. Resets the homing bit (bit 4) by setting it to 0. * 3. Sends the updated controlword to the device. * 4. Triggers the rising edge of the homing bit (bit 4) by setting it to 1. * 5. Sends the controlword to the device again to confirm the rising edge. * * @param {DeviceRef} deviceRef - Reference to the device for which the controlword will be updated. * @param {boolean} [clearHaltBit=true] - Indicates whether to clear the halt bit before configuring the homing procedure. * @returns {Observable} An observable that completes when the controlword has been successfully updated. */ setControlwordToStartHoming(deviceRef: DeviceRef, clearHaltBit?: boolean): Observable; /** * The firmware distinguishes between two types of parameters (configuration objects): * * - **Live objects:** Parameters read by the firmware during each loop, regardless of the CiA402 state of the device. * - **On-demand objects:** Parameters read by the firmware only when one of the following conditions is met: * - Communication with the master has just been established. * - Configuration has just been loaded from `config.csv`, `.assembly_config`, or `.factory_config` files. * - A transition in the CiA402 state machine from "Switch On Disabled" to "Ready to Switch On" occurs. * - The Fault Reset bit of the Controlword rises (only when the device is in a Fault State). * * This function will reset the fault if the device is in a fault state; * otherwise, it will transition the CiA402 state from the current state to "Switch On Disabled," and then to "Ready to Switch On." * This process ensures that the values of the on-demand parameters, which do not apply immediately, are correctly applied. */ forceOnDemandParametersUpdate(deviceRef: DeviceRef): Promise; /** * Executes a reset fault on the specified device. * * Resetting a fault can only be done from the FAULT CiA402 state by transitioning to SWITCH_ON_DISABLED. * This function will do the rising edge, that is it will first set the controlword reset fault bit to 0, wait a bit, and then set it to 1. * If the reset is successful, the fault reset bit will be set back to 0. * * @param {DeviceRef} deviceRef - Reference to the device for which the fault will be reset. * @param [force=false] - Indicates whether to force the fault reset even if the device is not in the FAULT CiA402 state. * @returns {Promise} Resolves when the reset fault operation is complete. */ resetFault(deviceRef: DeviceRef, force?: boolean): Promise; /** * Executes a quick stop on the specified device. * * A quick stop can only be initiated from the OPERATION_ENABLED state of the CiA402 state machine, transitioning to QUICK_STOP_ACTIVE. * * In CYCLIC_SYNC_TORQUE_MODE or TORQUE_PROFILE_MODE, the target torque and torque offset are set to 0 to prevent movement after the quick stop, as requested by the firmware team. * * @link https://www.wrike.com/open.htm?id=1452182434 * * @param {DeviceRef} deviceRef - Reference to the device on which the quick stop will be performed. * @param [force=false] - Indicates whether to force the quick stop even if the device is not in the OPERATION_ENABLED CiA402 state. * @returns {Promise} Resolves when the quick stop operation is complete. */ quickStop(deviceRef: DeviceRef, force?: boolean): Promise; /** * Reset targets. * * Set torque and velocity targets to 0, and set the position target to the current position value. */ resetTargets(deviceRef: DeviceRef): Promise; /** * Apply set point. * * When running in position profile mode and setting a new position target value, it's important to note that the device won't immediately move to the new position. * To execute a new position set-point or target value, you need to make certain changes to the controlword. * * To indicate that the new set-point is valid and should be executed, you need to trigger a rising edge of the new set-point bit in the controlword. * This rising edge serves as a signal to the device that a new set-point is being provided. * * Once the device receives the rising edge of the new set-point bit, it will set the set-point acknowledge bit in the statusword to 1. * This indicates that the device has acknowledged the new set-point and will execute the corresponding action, such as moving to the specified position. * * Afterwards, the device will signal its ability to accept new set-points by setting the set-point acknowledge bit back to 0 in the statusword. * This signifies that the device is ready to receive and process additional set-points. * * It's important to note that the device won't wait for the previous set-point to finish before executing a new set-point. * If you want to initiate a new set-point while the previous one is still being executed, you need to generate another rising edge of the new set-point bit in the controlword. */ applySetPoint(deviceRef: DeviceRef, setPointAckTimeout?: number): Promise; private waitForSetPointAcknowledge; /** * Release brake. * * Releases the brake when it is software-controllable (brakeReleaseStrategy 0x2004:04 !== 0). * If already released, returns immediately; otherwise sets brake status (0x2004:07) to 2 and * waits pullTime (0x2004:03) + waitTime milliseconds before returning. The firmware blocks motion * and motion-related OS commands until the pull time expires. * Has no effect when brakeReleaseStrategy is 0 (Manual output voltage). * * @param waitTime - Additional time in milliseconds to wait on top of the brake pull time after * releasing the brake (default: 50). */ releaseBrake(deviceRef: DeviceRef, waitTime?: number): Promise; /** * Engage brake. * * Engages the brake when it is software-controllable (brakeReleaseStrategy 0x2004:04 !== 0). * Sets brake status (0x2004:07) to 1 and waits waitTime milliseconds before returning. * Has no effect when brakeReleaseStrategy is 0 (Manual output voltage). * * @param waitTime - Time in milliseconds to wait after engaging the brake before returning (default: 50). */ engageBrake(deviceRef: DeviceRef, waitTime?: number): Promise; /** * Run OS command. * * The OS command is a standard way of triggering actions or services that cannot be accommodated through a single SDO upload/download. * * The Dictionary object 0x1023 is used for executing OS commands. The following is the subindex list and their meanings: * * - 1: Command (OCTET_STRING), 8 bytes * - Byte 0: OS command ID, OS commands are identified by number, and here we specify which OS command to run, for example, 0 is encoder register communication * - Byte 1-7: Service request data, the remaining 7 bytes serve as arguments to the OS command, specifying details such as what register to read the value from * - 2: Status (UNSIGNED8), 1 byte * - 0: last command completed, no errors, no response data * - 1: last command completed, no errors, response data available * - 2: last command completed, error, no response data * - 3: last command completed, error, response data available * - 100-200: command executing with percentage (100 = 0%, 200 = 100%) * - 255: command executing (if percentage display is not supported) * - 3: Response (OCTET_STRING), 8 bytes * - Byte 0: Same as subindex 2 * - Byte 1: unused * - Byte 2-7: Service response data, if the last command completed with response data, it will be available in these 6 bytes, for example, the value of the BiSS register * * Note that: * - As soon as the value of 1: Command Byte 0 changes, the OS command will start to execute. * - If the last command completed with response data, it will be available in bytes 2-7 of 3: Response subindex. * - The value of subindex 2: Status will be the same as that of 3: Response Byte 0. * * All possible cases of 0x1023:03 Response subindex: * * | Description | Byte 0 | Byte 1 | Byte 2 | Byte 3 | Byte 4 | Byte 5 | Byte 6 | Byte 7 | * |-------------------------------------------------------|:-------:|:------:|:-------------:|:------:|:------:|:------:|:------:|:------:| * | Command in progress with percentage | 100-200 | - | - | - | - | - | - | - | * | Command in progress without percentage | 255 | - | - | - | - | - | - | - | * | Command completed without errors and without response | 0 | - | - | - | - | - | - | - | * | Command completed without errors and with response | 1 | - | Data | Data | Data | Data | Data | Data | * | Command completed with error and without response | 2 | - | - | - | - | - | - | - | * | Command completed with error and with response | 3 | - | OS error code | Data | Data | Data | Data | Data | * * Note that in the case of "Command completed without errors and with response," 6 bytes can be used for data. * However, only 5 bytes are available in the case of "Command completed with error and with response." * This limitation arises because Byte 2 in the latter response is allocated for the OS error code. * The OS error code serves to indicate the reason behind the error occurrence. * * 0x1023: OS command is used in combination with 0x1024: OS command mode object. * In our firmware, only the values 0 and 3 from the 0x1024 command mode object (USINT) are handled, and their meanings are as follows: * - 0: Execute the next command immediately (default) * - 3: Abort the current command and all commands in the buffer * * Note that if you abort the OS command, you must switch the value of 0x1024 back to 0 before executing another OS command. * * @param deviceRef The reference to the device on which the command will be executed. * @param command The command to be executed, represented as a Uint8Array. * @param commandTimeout The maximum time allowed for the command to complete. * @param responsePollingInterval The interval (in milliseconds) for polling the command response. * @param osCommandMode Specifies whether the next OS command should run immediately after the current one or abort the current command. Sets the OS Command Mode. Defaults to false. * @param fsBufferContent If true, the content of the fs-buffer will be read and assigned to the `fsBuffer` property of {@link OsCommandResponse}. If a Uint8Array is provided, the content will be written to the fs-buffer file. If undefined, only the OS command will be executed, and its response will be read and parsed. * @param fsBufferReadWriteTimeout The timeout for reading/writing the fs-buffer content, in milliseconds. Defaults to 30000. * @returns An observable of type T, which extends {@link OsCommandResponse}, representing the result of the command execution. */ runOsCommand(deviceRef: DeviceRef, command: Uint8Array, commandTimeout: number, responsePollingInterval?: number, osCommandMode?: boolean | OsCommandMode, fsBufferContent?: boolean | Uint8Array, fsBufferReadWriteTimeout?: number): Observable; setOsCommandMode(deviceRef: DeviceRef, value: OsCommandMode): Observable; /** * Abort the OS command in progress and leave the OS command mode ready for the next command. * * Writing 0x1024:00 = 3 is sticky - it keeps aborting every command that follows until the mode is set * back to 0. This method performs the whole sequence: it reads the last response to learn whether a * command was actually in progress, requests the abort, polls 0x1023:03 until the drive stops reporting * a command in progress, and always resets the mode to * {@link OsCommandMode.EXECUTE_THE_NEXT_COMMAND_IMMEDIATELY} afterwards. Calling it with nothing in * progress is a safe way to clear a mode left at 3 by an earlier abort. * * Note that reading the response of a completed command resets the OS command to idle. The status * consumed that way is reported back as `lastStatus` / `lastErrorCode`. * * Unlike {@link MotionMasterReqResClient#runOsCommand}, a timeout does not throw: the returned result has * `request: 'failed'` and `timeout: true`, so the caller still learns what the drive last reported. Errors * from the underlying parameter reads and writes (an unreachable device, for example) are still thrown. * * @param deviceRef The reference to the device on which the OS command should be aborted. * @param commandTimeout How long to wait, in milliseconds, for the drive to stop reporting a command in progress. * @param responsePollingInterval The interval (in milliseconds) for polling the command response. */ abortOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Read and parse the OS command response, resolving to `undefined` when it cannot be read or parsed. * * {@link MotionMasterReqResClient#readOsCommandResponse} throws on an unknown status byte, and reading * 0x1023:03 can fail outright while the drive is busy executing a command. Neither is a reason to give up * on {@link MotionMasterReqResClient#abortOsCommand}, which needs the abort and the mode reset to happen * regardless of what the drive reports. */ private readOsCommandResponseOrUndefined; runEncoderRegisterCommunicationOsCommand(deviceRef: DeviceRef, encoderOrdinal?: number, slaveAddress?: number, rw?: number, registerAddress?: number, registerWriteValue?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runResetCirculoEncoderPositionOsCommand(deviceRef: DeviceRef, encoderOrdinal?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runIcMuCalibrationModeOsCommand(deviceRef: DeviceRef, encoderOrdinal?: number, modeEnable?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runOpenLoopFieldModeOsCommand(deviceRef: DeviceRef, parameterIndex?: number, parameterValue?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runHrdStreamingOsCommand(deviceRef: any, action?: HrdStreamingOsCommandAction, dataIndex?: HrdStreamingOsCommandDataIndex, duration?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runMotorPhaseOrderDetectionOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runCommutationOffsetMeasurementOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runOpenPhaseDetectionOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runPolePairDetectionOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runPhaseResistanceMeasurementOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runPhaseInductanceMeasurementOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runTorqueConstantMeasurementOsCommand(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runSmmAcyclicHandlerOsCommand(deviceRef: DeviceRef, command: Uint8Array, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean, fsBufferContent?: boolean | Uint8Array, fsBufferReadWriteTimeout?: number): Observable; runSkippedCyclesCounterOsCommand(deviceRef: DeviceRef, firmwareService?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runIgnoreBissStatusOsCommand(deviceRef: DeviceRef, trigger?: number, encoderOrdinal?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runSystemIdentificationOsCommand(deviceRef: DeviceRef, parameterIndex?: number, parameterValue?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runTriggerErrorOsCommand(deviceRef: DeviceRef, firmwareService?: number, errorType?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runKublerEncoderCommandOsCommand(deviceRef: DeviceRef, command: Uint8Array, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runUseInternalEncoderVelocityOsCommand(deviceRef: DeviceRef, trigger?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; runKublerEncoderRegisterCommunicationOsCommand(deviceRef: DeviceRef, rw?: number, registerAddress?: number, registerLength?: number, registerWriteValue?: number, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean): Observable; /** * Resets the multiturn position of the Kubler encoder to 0. * This function is available starting from firmware version SW00029_MagPac_w_crc_v0_9_202410221549.bin. */ resetKublerEncoderMultiturnPosition(deviceRef: DeviceRef): Observable; readOsCommandResponse(deviceRef: DeviceRef): Observable; runOsCommandAndWriteFsBuffer(deviceRef: DeviceRef, command: Uint8Array, fsBufferContent: Uint8Array, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean | OsCommandMode, fsBufferReadWriteTimeout?: number): Observable; runOsCommandAndReadFsBuffer(deviceRef: DeviceRef, command: Uint8Array, commandTimeout?: number, responsePollingInterval?: number, osCommandMode?: boolean | OsCommandMode): Observable; /** * Set halt bit. * * The behavior of the halt function (bit 8) in the controlword depends on the specific operation mode of the device. * When the halt bit is set to 1, the commanded motion will be interrupted, and the behavior of the device will follow the defined rules for the halt option code. * * After releasing the halt function by setting the halt bit to 0, the drive device will attempt to continue the commanded motion if possible, * based on the specific operation mode and the conditions of the system. */ setHaltBit(deviceRef: DeviceRef, value: boolean): Promise; getCachedDeviceByDeviceRefObj(deviceRefObj: DeviceRefObj): Device | undefined; /** * Reloads the firmware by transitioning the device to the EtherCAT BOOT state, unloading the current firmware and loading the bootloader. * Afterward, transitions back to OP mode, reloading the firmware during the INIT to PREOP phase. */ reloadFirmware(deviceRef: DeviceRef): Observable; /** * Performs a factory reset by deleting all files except those specified in the `filesToKeep` argument. * * Optionally installs an empty firmware after the file removal. * * If empty firmware is not installed: * - The currently installed firmware can optionally be reloaded. * - The file SOMANET_CiA_402.xml and its parts will not be removed. * * To retain multipart files (e.g., SOMANET_CiA_402.xml.zip.part000), include only the base name (e.g., "SOMANET_CiA_402.xml") in the `filesToKeep` list. */ factoryReset(deviceRef: DeviceRef, filesToKeep?: string[], installEmptyFirmware?: boolean, reloadFirmware?: boolean): Observable; /** * Computes the Feed Constant for a given device. * * The Feed Constant is calculated as the quotient of: * - `0x6092:01`: Feed * - `0x6092:02`: Shaft Revolutions * * @param deviceRef - Reference to the device for which the Feed Constant is computed. * @param requestTimeout - Optional timeout in milliseconds for the parameter request (default: 5000). * @returns An Observable that emits the computed Feed Constant as a number. */ computeFeedConstant(deviceRef: DeviceRef, requestTimeout?: number): Observable; /** * Computes the mechanical Gear Ratio for the specified device. * * The Gear Ratio is derived from device parameters representing: * - Motor-side revolutions (`0x6091:01`) * - Shaft-side revolutions (`0x6091:02`) * * Additionally, encoder assignments for the torque and position control loops * are retrieved to determine whether an external mechanical ratio is present. * * If both control loops use the same encoder source (non-zero and equal), * the returned ratio is `1`, indicating no external mechanical reduction. * * Otherwise, the ratio is computed as: * * motorRevolutions / shaftRevolutions * * If shaftRevolutions is `0` or unavailable, a fallback value of `1` is returned. * * @param deviceRef Reference to the device whose Gear Ratio is computed. * @param loadFromCache If true, previously cached parameter values will be used instead of initiating device requests. * @param requestTimeout Timeout (in milliseconds) applied when reading parameter values from the device. Defaults to `5000`. * * @returns An Observable emitting a numeric Gear Ratio. */ computeGearRatio(deviceRef: DeviceRef, loadFromCache?: boolean, requestTimeout?: number): Observable; /** * Save the modified parameter values to the config.csv file so that they are used the next time the device is power cycled. * The configuration is saved using the 0x1010: Store parameters object. */ saveConfig(deviceRef: DeviceRef): Observable; /** * Replace or merge the contents of the config.csv file with the provided data and instruct the device to load the updated configuration. * * The new configuration is loaded using the `0x1011:01 Restore All Default Parameters` command. * * This function performs several key operations to ensure consistency: * 1. **Resolve:** Determines the final content based on the strategy (Replace vs Merge). * 2. **Upload:** Writes the content to `config.csv` on the device. * 3. **Load:** Triggers the device to load the new settings from the file. * 4. **PDO Guard:** Identifies parameters mapped to RxPDOs and re-applies their values via SDO. This prevents the master's cyclic data (which may be zero) from immediately overwriting the new configuration. * 5. **Refresh:** Optionally reads the final values back from the device to update the local Motion Master cache. * * @param deviceRef A reference to the device where the configuration will be applied. * @param data The new configuration data to be written to the config.csv file (string or Uint8Array). * @param strategy The strategy to use when loading the configuration. * - `'replace'` (default): Overwrites the existing configuration file completely. * - `'merge'`: Reads the existing file, appends/updates it with the new data (input takes precedence), and writes the result back. * @param retryConfig Configuration settings for retrying the restore default parameters operation. * @param refresh A flag to refresh device parameter values after loading the new configuration. Defaults to `true`. * @returns An observable that emits `void` once the configuration has been successfully loaded and (optionally) refreshed. */ loadConfig(deviceRef: DeviceRef, data: Uint8Array | string, strategy?: LoadConfigStrategy, retryConfig?: RetryConfig, refresh?: boolean): Observable; /** * Checks if the device has firmware by reading the Manufacturer Software Version parameter (0x100A:00). */ hasFirmware(deviceRef: DeviceRef): Observable; /** * Reads the contents of configuration CSV files in the specified order and returns a list of unique configuration parameters. * If the files are provided in the order: '.factory_config', 'config.csv', '.assembly_config', this function * mimics the firmware's behavior during "Restore All Default Parameters," retaining only the most recent value of any duplicated parameter. * * If config files do not exist or cannot be parsed, the function will continue executing for any files that can be processed. */ getConfigFileParameters(deviceRef: DeviceRef, filenames?: string[]): Observable; /** * Retrieves the firmware version of the Kübler encoder by reading register address 4. * The returned number follows this format: 9240828, representing version 9 from August 28, 2024. */ getIntegroEncoderFirmwareVersion(deviceRef: DeviceRef): Observable; /** * Reads and parses the error register from an Integro integrated encoder. * * This method sends a command to the specified device to read the encoder error * register (register address 0x62, length 4 bytes) using the Kübler Encoder * Register Communication OS command protocol. * * The raw 32-bit register value returned by the device is automatically parsed * into a structured object containing: * - the extracted 16-bit error code, * - the associated 16-bit debug information, * - an optional human-readable error description if the code is recognized. * * @param deviceRef Reference to the target device from which to read the error register. * @returns An Observable that emits the parsed encoder error details. */ readoutIntegroIntegratedEncoderError(deviceRef: DeviceRef): Observable; /** * @todo Document this method and consider removing the void return type. */ runPhaseResistanceMeasurement(deviceRef: DeviceRef): Observable; /** * Sets the device mode of operation and then transitions the device * to the specified CiA 402 state. * * The operations are executed sequentially: * 1. The mode of operation is written to the device. * 2. The device is transitioned to the requested CiA 402 state. * * @param deviceRef - Reference to the target device. * @param modesOfOperation - Desired CiA 402 mode of operation. * @param cia402State - Target CiA 402 state to transition to. * * @returns Observable that completes when both operations finish. */ setModesOfOperationAndTransitionToCia402State(deviceRef: DeviceRef, modesOfOperation: ModesOfOperation, cia402State: Cia402State): Observable; /** * Installs the Integro Encoder Firmware by performing the following steps: * 1. Switches to the Kubler encoder bootloader firmware. * 2. Validates the firmware update size. * 3. Erases the existing encoder firmware. * 4. Writes the new firmware. * 5. Exits bootloader mode. * * @param deviceRef The reference to the device on which the firmware will be installed. * @param content The firmware content to be written, provided as a Uint8Array. * @returns An observable that emits {@link KublerEncoderCommandOsCommandResponse} upon completion of the installation. */ installIntegroEncoderFirmware(deviceRef: DeviceRef, content: Uint8Array): Observable; /** * @link https://www.wrike.com/open.htm?id=1375749957 * * @todo: Verify if the device is an ACTILINK-S device and check the corresponding variant file. */ isIntegroWithMultiturnEncoder(deviceRef: DeviceRef): Promise; /** * Fetches the UI feature configuration for a specified device. * * @param deviceRef - A reference to the target device. * @returns An object containing the UI feature configuration. */ getUIFeaturesConfig(deviceRef: DeviceRef): Promise; /** * Updates the grouped PDO (Process Data Object) parameter values for a specific device. * * This function processes the provided `pdoGroupedValues` sequentially. Each group of PDO values is filtered, * mapped, and padded with zeros (if necessary), before being sent to the device at the specified `pdoIndex`. * The update is done in order to ensure each group is updated one by one. * * The function performs the following steps for each grouped value: * 1. Clears the current PDO mapping for the specified device and PDO index. * 2. Sets the new parameter values. * 3. Updates the number of mapped parameters in the PDO. * * @param {DeviceRef} deviceRef - The reference to the device whose PDO parameters will be updated. * @param {number[][]} pdoGroupedValues - A 2D array where each inner array represents a group of PDO values. * The first element in each group is ignored, and the remaining values are processed. * @param {0x1600 | 0x1A00} pdoIndex - The PDO index to update, either `0x1600` for RxPDO or `0x1A00` for TxPDO. * * @returns {Promise} Resolves when all PDO parameter updates are complete. * The function processes and applies updates sequentially to ensure they are performed in order. */ updatePdoParameterGroupedValues(deviceRef: DeviceRef, pdoGroupedValues: number[][], pdoIndex: 0x1600 | 0x1a00): Promise; /** * Reads the SMM parameter for a given device. * * @param deviceRef - The reference to the device to which the command will be sent. * @param index - The index of the SMM parameter to read. * @param subindex - The subindex of the SMM parameter to read. Defaults to 0. * @param commandTimeout - The timeout for the command in milliseconds. * @param responsePollingInterval - The interval between polling attempts for a response in milliseconds. * * @returns An observable that emits the response from the command once it is received. */ readSmmParameter(deviceRef: DeviceRef, index: number, subindex?: number, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Reads the SMM parameter value as a number. * * This method reads a parameter from a device and extracts its value based on the provided `dataViewExtractor`. * The default behavior is to extract a 32-bit integer in little-endian format. * * @param deviceRef - A reference to the device from which the SMM parameter is being read. * @param index - The index of the parameter to read. * @param subindex - The subindex of the parameter (default is 0). * @param dataViewExtractor - A function that extracts a number from the `DataView` (default is `view.getInt32(0, true)`). * * @returns An observable that emits the extracted number value. * * @throws {Error} If the response buffer is empty or invalid. */ readSmmParameterNumberValue(deviceRef: DeviceRef, index: number, subindex?: number, dataViewExtractor?: (view: DataView) => number): Observable; /** * Reads the SMM parameter value as a string. * * This method reads a parameter from a device and decodes its value as a UTF-8 string from the response buffer. * * @param deviceRef - A reference to the device from which the SMM parameter is being read. * @param index - The index of the parameter to read. * @param subindex - The subindex of the parameter (default is 0). * * @returns An observable that emits the decoded string value. * * @throws {Error} If the response buffer is empty or invalid. */ readSmmParameterStringValue(deviceRef: DeviceRef, index: number, subindex?: number): Observable; /** * Reads the SMM parameter value as an array of numbers. * * This method reads a parameter from a device and returns the values as an array of numbers, * where each element corresponds to a byte from the response buffer. * * @param deviceRef - A reference to the device from which the SMM parameter is being read. * @param index - The index of the parameter to read. * @param subindex - The subindex of the parameter (default is 0). * * @returns An observable that emits an array of numbers, representing the byte values in the response buffer. * * @throws {Error} If the response buffer is empty or invalid. */ readSmmParameterArrayValue(deviceRef: DeviceRef, index: number, subindex?: number): Observable; /** * Reads the SMM firmware version from a device as an array of bytes. * * This method reads the firmware version (MCU Software Version 0x0001:00) of the device as a tuple of two numbers. * The first byte represents the minor version, and the second byte represents the major version. * * @param deviceRef - A reference to the device from which the firmware version is being read. * * @returns An observable that emits a tuple of two numbers, representing the byte values of the firmware version. */ readSmmFirmwareVersion(deviceRef: DeviceRef): Observable<[number, number]>; /** * Reads the SMM firmware version from a device as a number. * * This function retrieves a specific parameter from the device's SMM memory * and interprets the result as a 16-bit version number. * * @param deviceRef - A reference to the target device. * @returns An `Observable` emitting the firmware version, represented as an integer. */ readSmmFirmwareVersionAsNumber(deviceRef: DeviceRef): Observable; /** * Resolves the SMM parameter structure version for the specified device based on its firmware version. * * @param deviceRef - The reference to the target device. * * @returns An Observable that emits the appropriate SMM parameter structure version: * - 0x0041 for firmware versions below 2.3 (0x0203). * - 0x0203 for firmware versions 2.3 (0x0203) and above. * * @remarks * - The function first reads the firmware version of the device. * - Based on the firmware version, it returns the corresponding parameter structure version: * - If the firmware version is less than 0x0203, the parameter structure version is 0x0041. * - If the firmware version is 0x0203 or greater, the parameter structure version is 0x0203. */ resolveSmmParameterStructureVersion(deviceRef: DeviceRef): Observable; /** * Reads the SMM serial number from a device. * * This method reads the serial number of the device as a string. * The serial number is retrieved from the device using the appropriate SMM parameter (0x0003:00). * * @param deviceRef - A reference to the device from which the serial number is being read. * * @returns An observable that emits the serial number as a string. */ readSmmSerialNumber(deviceRef: DeviceRef): Observable; /** * Reads the SMM temperature value from a device. * * This method reads the temperature of the device as a number. The temperature is retrieved from the device * using the appropriate SMM parameter (0x000a:00). * * @param deviceRef - A reference to the device from which the temperature is being read. * * @returns An observable that emits the temperature value as a number. */ readSmmTemperature(deviceRef: DeviceRef): Observable; /** * Reads the SMM parameter check value from a device. * * This method reads the parameter check value from the device as a 16-bit unsigned integer. The value represents * the number of parameters available on the SMM and is retrieved from the device using the appropriate SMM parameter (0x000b:00). * and the custom data extraction function. * * @param deviceRef - A reference to the device from which the parameter check value is being read. * * @returns An observable that emits the parameter check value as a 16-bit unsigned integer, which represents * the number of parameters available on the SMM. */ readSmmParameterCheck(deviceRef: DeviceRef): Observable; /** * Reads the SMM maximum position discrepancy value from a device. * * This method reads the maximum position discrepancy value from the device as a 32-bit unsigned integer. * The value is retrieved from the device using the appropriate SMM parameter and the custom data extraction function. * * @param deviceRef - A reference to the device from which the maximum position discrepancy value is being read. * * @returns An observable that emits the maximum position discrepancy value as a 32-bit unsigned integer. */ readSmmMaxPositionDiscrepancy(deviceRef: DeviceRef): Observable; /** * Logs into the SMM for parameter download with the provided credentials. * * This function sends a login command to the device using the provided username and password. It returns an observable * that emits `true` if the login is successful and `false` otherwise. If the device is already logged in, the next login * attempt will fail unless the user logs out beforehand. * * @param deviceRef - The reference to the device to which the login command will be sent. * @param username - The optional username used for logging in to the SMM. If not provided, it will be treated as an empty string. * @param password - The password used for logging in to the SMM. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the login attempt fails. * * @remarks * If the device is already logged in, the next login attempt will fail unless the user logs out first. */ loginToSmmForParameterDownload(deviceRef: DeviceRef, username: string, password: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Logs into the SMM for software update with the provided credentials. * * This function sends a login command to the device using the provided username and password. It returns an observable * that emits `true` if the login is successful and `false` otherwise. If the device is already logged in, the next login * attempt will fail unless the user logs out beforehand. * * @param deviceRef - The reference to the device to which the login command will be sent. * @param username - The optional username used for logging in to the SMM. If not provided, it will be treated as an empty string. * @param password - The password used for logging in to the SMM. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the login attempt fails. * * @remarks * If the device is already logged in, the next login attempt will fail unless the user logs out first. */ loginToSmmForSoftwareUpdate(deviceRef: DeviceRef, username: string, password: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Logs out from the SMM. * * This function sends a logout command to the device and returns an observable that emits `true` if the logout * is successful and `false` otherwise. The command times out after 10 seconds if no response is received. * * @param deviceRef - The reference to the device to which the logout command will be sent. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the logout attempt fails. */ logoutFromSmm(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Logs out from the SMM and then logs back in with the provided credentials for parameter download. * * This function first sends a logout command to the device, followed by a login command using the provided username * and password. It returns an observable that emits `true` if both the logout and login attempts are successful * and `false` otherwise. The login process is handled through the `loginToSmmForParameterDownload` function. * * @param deviceRef - The reference to the device to which the logout and login commands will be sent. * @param username - The username used for logging in to the SMM. * @param password - The password used for logging in to the SMM. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If either the logout or login attempt fails. */ reloginToSmmForParameterDownload(deviceRef: DeviceRef, username: string, password: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Changes the SMM password for the specified device. * * @param deviceRef - A reference to the target device. * @param oldPassword - The current SMM password. * @param newPassword - The new password to set for the SMM. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the password change attempt fails. * * @remarks * A prior successful login is required before changing the password. * The new password must be at least 4 characters long. * * This function sends an acyclic command to update the password. If successful, it triggers an SMM restart. */ changeSmmPassword(deviceRef: DeviceRef, oldPassword: string, newPassword: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Triggers an SMM restart for the specified device. * * This method sends a command to the device to trigger an SMM restart and waits for a response. * The method will return `true` if the restart was successful, otherwise `false`. * * SMM may take up to 30 seconds to boot the newly flashed firmware during a software update, * with some variability in the exact duration. * * @param deviceRef - The reference to the device to restart. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the SMM restart attempt fails. */ triggerSmmRestart(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Acknowledges an I/O failure on the specified device. * * This method sends a command to the device to acknowledge an I/O failure and waits for a response. * The method will return `true` if the acknowledgment was successful, otherwise `false`. * * @param deviceRef - The reference to the device to acknowledge the I/O failure on. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the acknowledgment attempt fails. */ acknowledgeIoFailureOnSmm(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Configures the SMM software update process for the specified device. * Prepares the device to receive a software update of the given file size. * * @param deviceRef - A reference to the target device. * @param fileSize - The size of the software update file, in bytes. * * @throws {Error} If the configuration attempt fails. */ configureSmmSoftwareUpdate(deviceRef: DeviceRef, fileSize: number): Observable; /** * Performs a complete SMM software update on the specified device. * This includes authentication, configuration, data transmission in chunks, * CRC validation, and device restart. * * @param deviceRef - Reference to the target device. * @param username - Username used for authentication. * @param password - Password used for authentication. * @param buffer - The software update file as a `Uint8Array`. * @param crc - CRC checksum of the software update file for integrity verification. * @param chunkSize - (Optional) Size of each data chunk in bytes. Defaults to 1000. * @param commandTimeout - (Optional) Timeout for each OS command. Defaults to 60,000 ms. * @param responsePollingInterval - (Optional) Polling interval for command responses. Defaults to 1000 ms. * @param fsBufferReadWriteTimeout - (Optional) Timeout for fs-buffer read/write operations. Defaults to 120,000 ms. * * @throws {Error} If any step in the software update process fails. * * @remarks * The software update procedure follows these sequential steps: * 1. Log out from any existing SMM session. * 2. Authenticate and log in to the SMM device for software update. * 3. Configure the SMM device with the expected update file size. * 4. Transmit the file in data chunks (default: 1000 bytes each). * 5. Send the CRC checksum for data integrity validation. * 6. Finalize the software update. * 7. Trigger a device restart to apply the update. * * Each step is implemented as a deferred observable. * The commands execute only when subscribed to, ensuring a strict sequence. */ updateSmmSoftware(deviceRef: DeviceRef, username: string, password: string, buffer: Uint8Array, crc: number, chunkSize?: number, commandTimeout?: number, responsePollingInterval?: number, fsBufferReadWriteTimeout?: number): Observable; /** * Resolves whether an automated SMM software update is allowed for the specified device. * * This method evaluates the device and the provided firmware binary against a set of * preconditions required for automated installation. It returns a detailed * {@link SmmAutomatedUpdate} object describing each individual check result, which * can be used to give precise feedback to the user when automation is not possible. * * The automation is only permitted when **all** of the following conditions are met: * - The device is a recognized Somanet product (`isValidProduct`). * - The device belongs to the Circulo product family (`isCirculo`). * - The binary is encrypted (`isBinaryEncrypted`). * - The binary targets one of the supported SMM versions — v1.4 (260) or v2.56 (568) (`isAllowedBinaryVersion`). * - If targeting v2.56, the device SoC firmware version is ≥ 5.5.0 (`canInstallV256`). * - The device is running a legacy SMM firmware below v1.3, i.e. version < 259 (`isDeviceLw1`). * * If the device is not a recognized product, the method returns early with all flags set * to `false` and default zero values to avoid unnecessary device communication. * * @param deviceRef - A reference to the target device. * @param buffer - The SMM firmware binary to be installed, provided as a `Uint8Array`. * Its header is parsed to determine the target version and encryption status. * * @returns A promise that resolves to an {@link SmmAutomatedUpdate} object containing: * - `isValidProduct` — Whether the device maps to a known Somanet product. * - `isCirculo` — Whether the device belongs to the Circulo product family. * - `isCirculo7` — Whether the device is a Circulo 7. * - `isCirculo9` — Whether the device is a Circulo 9. * - `isDeviceLw1` — Whether the device SMM firmware is below v1.3 (version < 259). * - `isBinaryEncrypted` — Whether the provided firmware binary is encrypted. * - `isAllowedBinaryVersion` — Whether the binary targets a supported version (v1.4 or v2.56). * - `canInstallV256` — Whether v2.56 can be installed (requires SoC firmware ≥ 5.5.0). * - `isAutomationAllowed` — Whether all preconditions for automated update are satisfied. * - `allowedTargetSmmVersions` — The list of supported target SMM versions: `[260, 568]`. * - `deviceFirmwareVersion` — The SoC firmware version string read from the device (index `0x100a:0`). * - `deviceSmmVersion` — The current SMM firmware version as a raw integer. * - `binaryVersion` — The target SMM version encoded in the binary header. */ resolveSmmAutomatedUpdateConditions(deviceRef: DeviceRef, buffer: Uint8Array): Promise; /** * Performs an automated, multi-step SMM software update to an encrypted firmware version on a Circulo device. * * Before installing the target binary, this method evaluates the device state by calling * {@link resolveSmmAutomatedUpdateConditions}. Based on the result, it determines which * sequence of intermediate firmware versions must be installed first to transition the device * from unencrypted to encrypted firmware. * * The installation sequence depends on the current SMM version and device group: * - **Legacy (< v1.3) + Circulo 7**: v99.0 → v77.0 → target * - **Legacy (< v1.3) + Circulo 9**: v99.0 → v77.1 → target * - **v99.0 + Circulo 7**: v77.0 → target * - **v99.0 + Circulo 9**: v77.1 → target * - **v77.0 or v77.1**: target only * * If the device does not support streaming, `commandTimeout` is automatically extended to 420,000 ms. * * @param deviceRef - Reference to the target device. * @param username - Username used for SMM authentication. * @param password - Password used for SMM authentication. * @param buffer - The target encrypted firmware binary as a `Uint8Array`. * @param crc - CRC32 checksum of the target firmware binary for integrity verification. * @param chunkSize - (Optional) Size of each data chunk transmitted per step, in bytes. Defaults to 1000. * @param commandTimeout - (Optional) Timeout for each OS command in ms. Automatically overridden to 420,000 ms * if the device does not support streaming. Defaults to 30,000 ms. * @param responsePollingInterval - (Optional) Polling interval for command responses in ms. Defaults to 1000 ms. * @param fsBufferReadWriteTimeout - (Optional) Timeout for fs-buffer read/write operations in ms. Defaults to 120,000 ms. * * @returns An `Observable` that completes when the full installation sequence finishes successfully. * * @throws {Error} With message `'Unknown product. Cannot perform SMM software update.'` if the device * serial number does not map to a known Somanet product. * @throws {Error} With a descriptive message listing unmet preconditions if automation is not allowed — * e.g. the device is not a Circulo, the binary is not encrypted, the target version is * unsupported, the SoC firmware is below v5.5.0 (for SMM v2.56), or the device is * already on SMM v1.3+. * @throws {Error} If any individual firmware installation step fails during execution. */ updateSmmSoftwareToEncrypted(deviceRef: DeviceRef, username: string, password: string, buffer: Uint8Array, crc: number, chunkSize?: number, commandTimeout?: number, responsePollingInterval?: number, fsBufferReadWriteTimeout?: number): Observable; /** * Transmits SMM parameters to the specified device. * * @param deviceRef - The reference to the target device. * @param values - An array of data values to transmit. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the transmission fails or if the `values` array is empty. * * @remarks * - If the `values` array is empty, the function throws an error. * - The function constructs an OS command for transmitting the parameters and writes the packed buffer to the fs-buffer file. */ transmitSmmParameters(deviceRef: DeviceRef, values: DataType[], parameterStructureVersion?: number | undefined, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Loads the SMM parameters from the device for verification purposes. * * Sends the `LOAD_PARAMETERS_FOR_VERIFICATION` subcommand to the specified device and reads * the fs-buffer in response. The received byte buffer is XOR-masked with `0xFF` and * then unpacked using the provided or inferred parameter structure version. * * @param deviceRef - The reference to the device from which the parameters should be loaded. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @returns An Observable that emits the response from the device, containing the valid parameter values for verification * after the buffer is processed and reconstructed. * * @throws Will throw an error if the command fails or times out. */ loadSmmParametersForVerification(deviceRef: DeviceRef, parameterStructureVersion?: number | undefined, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Verifies a group of SMM parameters for the specified device. * * This function calculates a bitmask from the provided values and group ordinal, * then sends an SMM OS command (subcommand VERIFY_PARAMETERS) along with the bitmask content * via `fs-buffer` to the device for verification. * * @param deviceRef - A reference to the target device. * @param values - An array of parameter values to verify. * @param groupIndex - The verification group index used for bitmask calculation. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws {Error} If the verification fails. * * @remarks * This function requires parameters to be previously loaded for verification to succeed. If parameters are not preloaded, the verification will fail. * The same group can be verified multiple times without causing an error. */ verifySmmParameters(deviceRef: DeviceRef, values: DataType[], groupIndex: number, parameterStructureVersion?: number | undefined, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Loads the SMM validation file on the specified device. * * @param deviceRef - A reference to the target device. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * @returns An Observable emitting the OS command response. * * @remarks * This function should only be called **after all parameter groups have been successfully verified**. */ loadSmmValidationFile(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Loads the SMM validation file and then retrieves the safety parameters report file. * * @param deviceRef - A reference to the target device. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * @returns An Observable emitting the decoded content of the `.safety_parameters_report` file. * * @throws An error if loading the validation file fails. * * @remarks * This function should only be called **after all parameter groups have been successfully verified**. */ loadSmmValidationFileAndReadSafetyParametersReportFile(deviceRef: DeviceRef, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Validates the SMM configuration on the specified device. * * @param deviceRef - The reference to the target device. * @param report - A `Uint8Array` representing the validation report data. * @param date - The date associated with the validation. * @param username - The username used for authentication. * @param password - The password used for authentication. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws An error if the validation fails. * * @remarks * - Packs the validation report, date, username, and password into a buffer. * - Constructs an OS command using the `VALIDATE_CONFIGURATION` subcommand. * - Sends the command to the device and writes the packed buffer to the fs-buffer file. * - **Important:** Once the configuration is successfully validated, subsequent calls to this function will fail. To revalidate, the user must go through the verification process again. */ validateSmmConfiguration(deviceRef: DeviceRef, report: Uint8Array, date: Date, username: string, password: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Reads the safety parameters report from the device and validates the SMM configuration. * * @param deviceRef - The reference to the target device. * @param date - The date associated with the validation. * @param username - The username used for authentication. * @param password - The password used for authentication. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @param responsePollingInterval - The interval in milliseconds between polling for the response. * * @throws An error if the safety parameters report file is missing or if the validation fails. * * @remarks * - The function attempts to retrieve the `.safety_parameters_report` file from the device. * - If the file is missing, an error is thrown. * - The file content is read into a `Uint8Array` and passed to `validateSmmConfiguration`. * - The SMM configuration validation follows the same behavior as `validateSmmConfiguration`: * - If validation succeeds, subsequent calls to this function will fail. * - To revalidate, the user must repeat the verification process. */ readSafetyParametersReportAndValidateSmmConfiguration(deviceRef: DeviceRef, date: Date, username: string, password: string, commandTimeout?: number, responsePollingInterval?: number): Observable; /** * Retrieves SMM OD (Object Dictionary) parameters for a specific device. * * This function fetches and processes the safety parameters from the SMM object dictionary (JSON file), * transforming them into a consistent `SmmParameter` format for the provided device serial number. * It supports resolving the parameter structure version if not explicitly provided. * * @param deviceRef - The reference to the target device. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * @param useValues - Specifies which source of values to use: * - 'default': Uses the default factory values. * - 'reset': Uses the reset values. * - 'device': Uses the current values from the device. * Defaults to 'default'. * @param loadFromCache - Whether to load parameters from cache (`true`) or force a fresh load (`false`). Defaults to `true`. * * @returns An `Observable` emitting an array of `SmmParameter` objects, each representing a processed * parameter with metadata such as type, access rights, and UI-related configurations. * * @throws {Error} If the parameter structure version cannot be resolved or the SMM object dictionary fails to load. */ getSmmOdParameters(deviceRef: DeviceRef, parameterStructureVersion?: number | undefined, useValues?: 'default' | 'reset' | 'device', loadFromCache?: boolean): Observable; /** * Retrieves SMM OD (Object Dictionary) parameters for a specific device, grouped by their `group` property. * * This function fetches and processes the safety parameters from the SMM object dictionary, * then organizes them into a `Map` where each key represents a unique group, and the value is an array * of corresponding `SmmParameter` objects belonging to that group. * * @param deviceRef - The reference to the target device. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * @param useValues - Specifies which source of values to use: * - 'default': Uses the default factory values. * - 'reset': Uses the reset values. * - 'device': Uses the current values from the device. * Defaults to 'default'. * @param loadFromCache - Whether to load parameters from cache (`true`) or force a fresh load (`false`). Defaults to `true`. * * @returns An `Observable` emitting a `Map`: * - The keys are group names. * - The values are arrays of parameters belonging to the respective group. * * @throws {Error} If the parameter structure version cannot be resolved or the SMM object dictionary fails to load. * * @remark * The resulting groups are sorted to ensure their index matches the order expected by the `verifySmmParameters` function. * Additionally, parameters within each group are sorted in the sequence required for correctly packing verification values. * This ensures consistency between retrieval, packing, and verification stages. */ getSmmOdGroupedParameters(deviceRef: DeviceRef, parameterStructureVersion?: number | undefined, useValues?: 'default' | 'reset' | 'device', loadFromCache?: boolean): Observable>; /** * Performs a factory reset on the SMM parameters of the specified device. * It restores all safety-related parameters to their default reset values. * * @param deviceRef - A reference to the target device. * @param parameterStructureVersion - (Optional) A specific SMM parameter structure version to use. * If not provided, the version is resolved dynamically from the device. * * @throws {Error} If the factory reset operation fails. * * @remarks * This function first determines the SMM parameter structure version — either from the provided argument * or by resolving it from the device. It then extracts the reset values from the safety parameters * and transmits them to the device. */ factoryResetSmm(deviceRef: DeviceRef, parameterStructureVersion?: number | undefined): Observable; readCirculoEncoderExternalRegister(deviceRef: DeviceRef, encoderOrdinal: number, i2cDeviceId: CirculoIntegratedEncoderI2CDeviceId, registerAddress: number, commandTimeout?: number): Observable; /** * Writes a value to an external I²C register of a Circulo Integrated Encoder device (e.g., iC-PVL or EEPROM), * by issuing a series of register configuration commands through the iC-MU I²C communication bridge. * * The function sets up the I²C device ID, retry count, target register, and data value to be written, * and then triggers the `I2C_COM` command to initiate the write transaction over the external I²C bus. * * This is typically used to write configuration or operational parameters to EEPROM or iC-PVL RAM registers. * * @param deviceRef - Reference to the connected device used for communication. * @param encoderOrdinal - Index of the encoder on the bus (typically 1 if only one encoder is present). * @param i2cDeviceId - I²C device ID specifying the target external device (EEPROM, PVL limited, or PVL full). * @param registerAddress - Target register address on the external I²C device. * @param registerValue - Value to write to the specified register. * @param commandTimeout - Optional timeout in milliseconds for each command (default: 2000 ms). * * @returns An `Observable` that emits the final response * from the OS command sequence, confirming the write operation. */ writeCirculoEncoderExternalRegister(deviceRef: DeviceRef, encoderOrdinal: number, i2cDeviceId: CirculoIntegratedEncoderI2CDeviceId, registerAddress: number, registerValue: number, commandTimeout?: number): Observable; /** * This is a special function that reads the key configuration registers of a Circulo integrated encoder. * It sends a series of commands to the device to read the registers and returns the responses as an array. * It was added as part of a fix for the EEPROM issue in Circulo integrated encoders. * * @param deviceRef - The reference to the device to which the command will be sent. * @param encoderOrdinal - The ordinal number of the encoder. * @param commandTimeout - The timeout in milliseconds for the command to complete. * @returns An observable that emits an array of `EncoderRegisterCommunicationOsCommandResponse` objects. */ readCirculoIntegratedEncoderKeyConfigurationRegisters(deviceRef: DeviceRef, encoderOrdinal: number, commandTimeout?: number): Observable; /** * Writes the integrated encoder configuration to a binary file on the device. * * The function reads all key encoder configuration registers, converts them * into a binary format, and saves them as a `.bin` file on the device. * * ⚠️ **When to call**: * This should be invoked **after encoder configuration and calibration** have been * completed, so that the correct values are stored for persistence. * * ℹ️ **How the file is used**: * On firmware initialization, the device checks the encoder configuration. * If it detects an incorrect or missing configuration, the firmware will * automatically reconfigure the encoder using the parameters stored in this * binary file. * * 📄 **File naming**: * The written files are named based on the encoder ordinal: * - `circulo_integrated_encoder_1_config.bin` for encoder ordinal **1** * - `circulo_integrated_encoder_2_config.bin` for encoder ordinal **2** * * @param deviceRef - Reference to the target device. * @param encoderOrdinal - Encoder index/ordinal to identify which encoder to store configuration for. * @param commandTimeout - Optional timeout in milliseconds for the read commands (default: 5000). * @returns An observable that completes once the binary file has been written to the device. */ writeCirculoIntegratedEncoderConfigBinFile(deviceRef: DeviceRef, encoderOrdinal: number, commandTimeout?: number): Observable; /** * Retrieves the supported analog input (AI) modes for the specified device. * * Resolves the device reference, fetches the supported AI options and firmware version, * then combines these to determine which AI modes are enabled or disabled. * Certain AI inputs are disabled based on the device's Integro variant options. * * @param deviceRef - A reference to the device for which to fetch supported AI modes. * @returns An Observable emitting a two-dimensional array of numbers, where each inner array corresponds to an AI pin * and contains the supported modes. Pins with all modes disabled default to `[0]`. */ getSupportedAis(deviceRef: DeviceRef): Observable; /** * Retrieves the supported digital input/output (DIO) pin modes for a given device. * * This method resolves the device reference, fetches both the supported DIO options and firmware version, * then combines this information to determine which DIO pin modes are enabled or disabled. * It also disables specific DIO pin modes based on the device's Integro variant options. * * @param deviceRef - A reference to the device whose supported DIO pin modes are being fetched. * @returns An Observable that emits a two-dimensional array of numbers. Each inner array corresponds to a DIO pin * and lists the supported pin modes. If all pin modes for a pin are disabled, the array defaults to `[0]`. */ getSupportedDios(deviceRef: DeviceRef): Observable; /** * Checks the Circulo encoder error status registers for a specified encoder ordinal. * * This method queries two status registers (STATUS0 and STATUS1) for the given encoder * on the device, then maps the register values to an array of encoder error objects. * * @param deviceRef - Reference to the device. * @param encoderOrdinal - The ordinal/index of the encoder to check. * @returns An Observable that emits an array of EncoderRegisterError objects representing * all errors found in the queried encoder status registers. */ checkCirculoEncoderErrors(deviceRef: DeviceRef, encoderOrdinal: number): Observable; /** * Uploads and configures SMM parameters on the specified device from a CSV configuration file. * * This function performs the following steps in sequence: * 1. Parses the CSV config file into structured parameters. * 2. Resolves the SMM parameter structure version for the device. * 3. Groups and maps parameters according to the SMM Object Dictionary. * 4. Validates that the parameter counts match between the config and SMM structure. * 5. Logs out from the SMM if already logged in. * 6. Logs in for parameter download using provided credentials. * 7. Transmits the parameters to the device. * 8. Verifies transmitted parameters by reloading and matching values. * 9. Sequentially verifies each parameter group on the device. * 10. Loads and validates the safety parameters validation file. * 11. Reloads the SMM parameters to refresh the stored values. * 12. Ensures proper logout in all cases, including errors. * * @param deviceRef - Reference to the target device to configure. * @param username - Username used to log in for parameter download. * @param password - Password used to log in for parameter download. * @param configFileContent - The raw CSV content of the configuration file. * * @returns An Observable that emits a generated safety parameters report on success. * On failure at any step, it emits an error with a descriptive message. * * @remarks * This method uses RxJS operators to ensure that each asynchronous step completes before the next begins. * It also guarantees logout from the device when the operation finishes or if any error occurs. * * --- * * ⚠️ **WARNING: SAFETY-CRITICAL APPLICATION & MANDATORY COMPLIANCE** * * 1. **Scope of Automation** * This script is designed to automate the parameterization of Safe Motion Module. * Use of this script is strictly limited to configurations where a known, valid configuration (.csv) is already available. * * 2. **Mandatory Checklist Adherence** * Execution of this script does **NOT** bypass the requirements outlined in the * “Commissioning of Joints with Known Safety Configuration” checklist. * The user must ensure all physical prerequisites are met, including: * - Correct mechanical mounting per IEC 61800-5-2:2016. * - Proper encoder calibration. * - Verification that the FSoE Watchdog is correctly configured on the FSoE Master. * * 3. **Validation of Limits and Reactions** * As per standard operating procedure, * the safety configuration must be manually checked by * intentionally violating limits to trigger and verify the expected reaction. * If safe torque values are used, they must be validated by applying specific torque and verifying the reported data. * * 4. **System-Level Functional Testing** * Automation of individual drive parameters does not validate the safety of the machine. * The user is legally required to validate the safety functions of the entire system by * triggering every implemented safety function, including establishing a process for repeated testing of STO/SBC functions. * * 5. **Liability and Archiving** * The developer is not liable for configurations that produce violations during regular operation; * safety margins must be manually adjusted. * Upon completion, the user **MUST** export and archive the safety parameter report along with the commissioning checklists. * * **BY EXECUTING THIS SCRIPT, * YOU ACKNOWLEDGE THAT YOU HAVE COMPLETED ALL PRE-COMMISSIONING STEPS * AND WILL PERFORM ALL POST-COMMISSIONING VALIDATION TESTS LISTED IN THE PROJECT CHECKLIST.** */ configureSmmFromFile(deviceRef: DeviceRef, username: string, password: string, configFileContent: string): Observable; /** * Executes a forward call by sending the provided data, then parses the JSON response. * * @param data - The data to send. Can be a Uint8Array, an object (which will be JSON-stringified), or a string. * @param requestTimeout - Optional timeout for the request in milliseconds. Defaults to 5000 ms. * @param messageId - Optional message identifier. * * @returns An Observable that emits the parsed JSON response object upon a successful call. * * @throws Will throw an error if: * - `data` is not a Uint8Array, string, or object. * - The forward call fails. * - The response cannot be parsed as valid JSON. * * @example * ```ts * const data = { command: 'status' }; * this.executeForwardCallAndParseResponse(data) * .subscribe({ * next: (response) => console.log('Parsed response:', response), * error: (err) => console.error('Error:', err), * }); * ``` */ executeForwardCallAndParseResponse(data: Uint8Array | string | object, requestTimeout?: number, messageId?: string): Observable; /** * Auto-tunes the notch filter parameters based on the device's plant model. * * @param deviceSerialNumber - The serial number of the target device. * @returns An `Observable` that emits the parsed notch filter configuration upon success. * * @throws Will throw an error if: * - `deviceRef` is invalid. * - The device does not have a plant model. * - The forward call to the device fails. * - The auto-tune notch filter does not return finite valid values. * - The response cannot be parsed as valid JSON. */ autoTuneNotchFilter(deviceRef: DeviceRef): Observable; /** * * Writes notch filter parameter values to the specified device. * * This method sets the individual parameters of the notch filter (0x2023) on the device: * - Subindex `0x01` → enabled flag * - Subindex `0x02` → center frequency (rounded to nearest integer) * - Subindex `0x03` → rejection band (rounded to nearest integer) * - Subindex `0x04` → depth * * @param deviceRef - Reference to the target device. * @param notchFilter - Notch filter values to write to the device. * @param requestTimeout - Optional timeout in milliseconds for the request (default: 1000). * @returns An `Observable` that completes when the parameter values have been written successfully. * */ setNotchFilterParameterValues(deviceRef: DeviceRef, notchFilter: NotchFilter, requestTimeout?: number): Observable; /** * Deletes all HRD data files (`hr_data0.bin` to `hr_data4.bin`) from the device. * * The operation attempts to remove each file sequentially, regardless of whether * it exists or not. Missing files do not cause the sequence to stop or fail. * * @param deviceRef - Reference to the target device. * @returns An observable that completes once all delete operations have finished. */ removeAllHrdFiles(deviceRef: DeviceRef): Observable; /** * Reads a sequence of HRD files (`hr_data0.bin` to `hr_data4.bin`) from a device, * combines their contents into a single `Uint8Array`, and returns it as an Observable. * * Each file is read sequentially. If a file is missing or its content is `null`/`undefined`, * it is treated as an empty `Uint8Array`, so the sequence continues without errors. * * @param deviceRef - Reference to the device from which the files are read. * @returns An `Observable` that emits a single `Uint8Array` containing * the combined contents of all read files. */ readAllHrdFiles(deviceRef: DeviceRef): Observable; /** * Runs HRD streaming on the device. * * The procedure performs the following steps: * 1. Configures HRD streaming with the specified data index and duration. * 2. Starts the streaming process. * 3. Reads and combines all HRD files once streaming completes. * * @param deviceRef - Device to stream from. * @param dataIndex - Index of the HRD streaming data (default is 0). * @param duration - Streaming duration in milliseconds (default is 1000). * @returns Observable that emits a combined `Uint8Array` containing all HRD file data. */ runHrdStreaming(deviceRef: DeviceRef, dataIndex?: HrdStreamingOsCommandDataIndex, duration?: number): Observable; /** * Executes a chirp signal on the drive for system identification purposes. * * This method sends a sequence of system identification commands to the drive, configuring * the necessary parameters and optionally starting HRD streaming if requested. * * Key points: * - By executing the chirp signal on the drive, the firmware provides a very clean signal * to the motion controller without communication jitter. * - The sine profile is used for system identification purposes. * - This profile is not available as a standard Motion Profile type (0x6086). * * Requirements for the drive to correctly follow the trajectory: * - The drive must have the correct commutation offset angle configured. * - The encoder for the selected control method must be functional. * - The controller must be tuned appropriately. * * Limitations: * - The statusword cannot report the status of the profiler for this sine profile type. * It does not differentiate between different motion profile types. * - If any parameter is out of range or the start frequency is greater than the target * frequency, the drive will report an "Invalid Parameter" error. * - If the start and target frequencies are equal, the output wave frequency will be constant (static sine). * * Implementation notes: * - The generated chirp signal is added to the control loop as an additional demanded torque, * just after the notch filter. * - This allows system identification in CST, CSV, or CSP modes (or other profile modes). * * @param deviceRef - Reference to the target device. * @param options - Configuration options for the chirp signal, including: * - `modesOfOperation` (optional): Modes of operation to configure before starting. * - `startFrequency`: Frequency at which the chirp begins. * - `targetFrequency`: Frequency at which the chirp ends. * - `targetAmplitude`: Amplitude of the chirp signal. * - `transitionTime`: Time for frequency/amplitude transition. * - `signalType`: Type of signal to generate. * - `startProcedure`: If set to `WAIT_FOR_HRD_STREAMING_TO_START`, the OS command for executing * the chirp signal will wait for HRD streaming to start before running the chirp. * * @returns An observable that completes after the chirp signal sequence is finished. * If `startProcedure` is set to `WAIT_FOR_HRD_STREAMING_TO_START`, HRD streaming * will also be executed. */ runChirpSignal(deviceRef: DeviceRef, options: ChirpSignalOptions): Observable; /** * Retrieves the PDO mapping for the given device. * * This method attempts to get the device-specific UI configuration and returns * its PDO mapping. If the device does not have a specific UI configuration or * its PDO mapping is missing, the default PDO mapping (`uiConfigWithDefaultPdoMapping`) * is returned instead. * * @param deviceRef - Reference to the device for which the UI configuration is requested. * @returns An `Observable` that emits the RX and TX PDO mapping for the device. */ getUiConfigOrDefaultPdoMapping(deviceRef: DeviceRef): Observable; /** * Runs the offset detection procedure for the given device and emits step-wise progress updates. * * The procedure executes a sequence of diagnostic steps sequentially and reports their state * (`idle`, `running`, `succeeded`, `failed`) via an observable stream. * * Behavior * - If `stepIds` is provided, only those steps are executed (in order). * - If `stepIds` is empty, all available offset detection steps are executed. * - Automatically inserts `motorPhaseOrderDetection` if required by * `commutationOffsetMeasurement`. * - Transitions the device into diagnostics mode and ensures it is in * `OPERATION ENABLED` state before executing steps. * - Restores the brake state and transitions the device to * `SWITCH_ON_DISABLED` after completion, error, or cancellation. * - Certain steps may temporarily release or engage the brake as needed during execution. * * Cancellation * - Unsubscribing from the returned observable cancels further step execution. * - Cancellation stops the sequence cooperatively (in-progress async operations may still complete). * - Cancellation is treated as an error internally. * * Error Handling * - Emits an error if the device is not in the required CIA402 state. * - Emits an error if any step fails. * - Emits an error if step dependencies are violated. * - Cleanup operations (brake restore and state transition) are always attempted in `finally`. * * @param deviceRef - Reference to the target device. * @param stepIds - Optional list of step IDs to execute. If omitted or empty, all steps are executed. * @param brakeReleaseWaitMs - Additional time in milliseconds to wait on top of the brake pull time * (0x2004:03) after releasing the brake before proceeding with each diagnostic step that requires * an open brake. If the brake does not fully release in time, ensure the brake pull time * (0x2004:03) is correctly configured for your hardware (default: 50). * @param brakeEngageWaitMs - Time in milliseconds to wait after engaging the brake before proceeding * with each diagnostic step that requires an engaged brake (default: 50). * @returns An observable that emits the progress and final state of each offset detection step. * * @remarks * Each emission contains a cloned snapshot of all steps to allow safe external consumption * without mutation side effects. */ runOffsetDetection(deviceRef: DeviceRef, stepIds?: OffsetDetectionStepId[], brakeReleaseWaitMs?: number, brakeEngageWaitMs?: number): Observable; /** * Returns the display unit string for a device parameter, adjusted for the device's current * SI unit velocity setting (0x60A9) and feed constant configuration (0x6092:01). * * The feed constant is considered enabled when 0x6092:01 is a positive value other than 0xFFFFFFFF. * When enabled, velocity and position units are expressed in feed units (e.g. `mm/min`) instead of * the raw SI unit (e.g. `rpm`). Parameters not affected by these settings are returned unchanged. * * @param deviceRef - Reference to the device to read configuration from. * @param index - Object dictionary index of the parameter. * @param subindex - Object dictionary subindex of the parameter. * @param unit - Base unit string as stored in the parameter metadata (e.g. `"Inc"`, `"rpm"`). * @returns The formatted unit string for display purposes. */ getDeviceParameterFormattedUnitDisplay(deviceRef: DeviceRef, index: number, subindex: number, unit: string): Promise; }