Munic Box is connected to the vehicle bus, so Munic Box does interfere with the vehicle.
By installing Munic Box you acknowledge this risk and Mobile Devices Ingénierie can not be taken responsible for any trouble, harm, liability and injury caused by such connection.
Defer to your vehicle’s warranty provisions and owner’s instructions for guidance on whether any OBD II connector product might void or alter your vehicle’s warranty. Mobile Devices Ingénierie is not responsible for any costs or expenses associated with vehicle repairs or voided warranties.
If you notice any change in engine performance after connecting the device, disconnect the device immediately and contact Munic Box support. Do not use the device if it affects engine performance or acceleration in your particular make and model of vehicle.
Mobile Devices Ingénierie can, on demand, provide recommendation regarding the usage of OBD dongle & APIs.
drop
action.EcuDescription
: The list of ECUs and the way to communicate with itCommand
: The full definition of the command that will be sent to the deviceAction
: The operation that will be done with the result of previous commands and actionsname
(regexp [a-zA-Z][a-zA-Z0-9_]*[a-zA-Z0-9]
), It has to :
This name
attribute is used to refer to a particular object in another object's dependencies (for example, a command will depend on an ECU, an action will depend on one or several commands).
The base structure of the script is the obdStack
object. It has only one attribute, name
, which is a string name for the stack.
{
"obdStack": {
"name": "myStackName",
"ecuDescription": [
{ }
],
"obdCommand": [
{ }
],
"canFrameCommand": [
{ }
],
"canCommand": [
{ }
],
"canFrameReceive": [
{ }
],
"klineCommand": [
{ }
],
"j1850Command": [
{ }
],
"j1939Command": [
{ }
],
"j1708Command": [
{ }
],
"j1587Command": [
{ }
],
"tp2Command": [
{ }
],
"sleepCommand": [
{ }
],
"expressionDefinition": [
{ }
],
"actionList": [
{ }
]
}
}
The ECUs are described with the following elements:
MANDATORY
name
: The name of the ECU, will be used by commands to specify an ECU if needed.type
: the type of connection for the ECU. Possibilities are "can, "GMLAN", "kline". For retrocompatibility, if not present, type
will be "can".CAN related options
Connection
canConnection
: Allows to specify the bus to use. Default is
ALL: use any connected bus (contact us for details about pin switching
capabilities).canBaudRate
: Default is 500000. specify the speed of the bus if you want to restrict it. Common values are 250000 or 500000.defaultReplyTimeOutMS
: The default value is 100 (ms). The timeout before hanging up if no answer received. It is a long int in
milliseconds. It can varies between 50 and 10000 ms.Addressing
srcId
(Mandatory if type is "can" or "GMLAN"): the source Id. Is an hexadecimal string, length MUST be 3 or 8.dstId
(Mandatory if type is "can"): the destination Id. Is an hexadecimal string, length MUST be 3 or 8.dstIds
(Can replace dstId): is an array of dstId
. Is an hexadecimal string array, length of each element MUST be 3 or 8.addressType
: Default value is PHYSICAL. A string that can be one of these strings : FUNCTIONAL (receive all messages) or PHYSICAL
(receive one message only).canAddressingMode
: Default is NORMAL. To be set to EXTENDED when using extended addressing on CAN 11 bits (this is not related to CAN 29 bits addressing).canExtendedAddress
: Default is 0. It is an integer used as a byte whenever canAddressingMode is EXTENDED.canExtendedAddressMask
: Default is not used. It is an integer used as a extended address mask on answers (0x00 means everything, 0xFF limits to address). (depends on canExtendedAddress
).canExtendedAddressFilter
: Default is not used. It is an integer used as a extended address filter on answers. (depends on canExtendedAddress
).canIdType
: specifies if can is 11 or 29 bits, default value is 11BITS, other value is 29BITS.canMask
: Default value is 0x7FF if 11 bit can or 0x1FFFFFFF if 29 bits can. Mask as an hexadecimal string used for CAN raw commands when connected to CAN.canPaddingValue
: The value to pad the data with (hexadecimal format: "FF"
). Default is "00"
. To specify no padding,
put "-1"
.blocksize
: The blocksize _u8 value for non standard IsoTp. If not set, set to 0.separTime
: The separe time _u8 value for non standard IsoTp. x00-0x7F : 0-127 ms, 0x80-0xF0 : reserved, 0xF1-0xF9 : 100us-900
us, 0xFA-0xFF : reserved. If not set, set to 0.GMLAN related options
USDT
(Mandatory, replaces dstId
): the address for the USDT response. Is an hexadecimal string, length MUST be 3 or 8.UUDT
(Mandatory, replaces dstId
): the address for the UUDT response. Is an hexadecimal string, length MUST be 3 or 8.uudtTimeOutMS
: specific timeout value to use for the UUDT answer (the USDT timeout is still defined by defaultReplyTimeOutMS
).KLine related options
sourceAddress
: the source address, in string format, with the prefix "0x" (Default is 0xF1).targetAddress
: the target address of the ECU, in string format, with the prefix "0x" (Default is 0x33).forceLengthByte
: (most of time false) Boolean. If true, the lenght byte of the frame format will be found in every frames, even if not relevant.addressType
: Can be either "FUNCTIONAL" (by default) or "PHYSICAL".NOTE: not specifying canExtendedAddressMask
and canExtendedAddressFilter
but activating canExtendedAddress
implies to use the default filtering on the address data field (for example 123#F140 as question will get 123#F140 as a valid answer, but
140#F123 will be filtered out).
{
"ecuDescription": [
{
"name": "simple_ecu",
"srcId": "7E0",
"dstId": "7E8"
},
{
"name": "engine_ecu",
"srcId": "18DAF111",
"dstId": "18DB33F1",
"defaultReplyTimeOutMS": 1000,
"canPaddingValue": "0D",
"canConnection": "CAN-OBD",
"canBaudRate": 500000,
"canIdType": "29BITS"
},
{
"name": "shield_ecu",
"srcId": "7E0",
"dstIds": ["023", "7E8", "03F"],
"addressType": "PHYSICAL",
"defaultReplyTimeOutMS": 100,
"canAddressingMode": "EXTENDED",
"canExtendedAddress": 96,
"canExtendedAddressMask": 255,
"canExtendedAddressFilter": 241,
"canBaudRate": 500000,
"canIdType": "11BITS",
"canPaddingValue": "00"
},
{
"name": "simple_kline_ecu",
"type": "kline",
"sourceAddress": "0xF1",
"targetAddress": "0x33",
"forceLengthByte": false,
"addressType": "FUNCTIONAL"
},
]
}
Currently supported commands are:
{"obdCommand":[
is an array of standard OBD commands{"canFrameCommand":[
is an array of single frame CAN commands{"canCommand":[
is an array of multi-frame CAN commands{"tp2Command":[
is an array of CAN TP2 commands{"gmlanCommand":[
is an array of GMLAN commands{"klineCommand":[
is an array of KLine commands{"j1850Command":[
is an array of J1850 commands{"j1939Command":[
is an array of J1939 commands{"j1708Command":[
is an array of J1708 commands{"j1587Command":[
is an array of J1587 commands{"sleepCommand":[
is an array of "sleep" commands. Can be used to add a waiting time between commands.{"canFrameReceive":[
listen-only mode for CAN{"canPolling":[
high-frequency polling for CANEach command returns a sequence of bytes
: byte[]
, on which operations can be executed thanks to actions
.
Fields description
name
: the name of the command, will be later used by actions.mode
: the mode of the OBD command. is an hexa string.pid
: the pid of the OBD command, is an hexadecimal string. It is uneeded for DTC modes (3,4,7 and 0A) but indispensable for other modes.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"obdCommand": [
{
"name": "OBD_010D",
"mode": "01",
"pid": "0D"
},
{
"name": "OBD_010C",
"mode": "01",
"pid": "0C",
"forbiddenRawFilters": [
{
"mask": [0, 255],
"filters": [[0, 128]]
}
]
}
]
}
Used to send raw CAN frames.
Fields description
name
: the name of the command, will be later used by actions.ecu
: the identifier of the ECU to contact. Can either be on 3 bytes or 8 bytes. It is an hexadecimal string.data
: the data to send, as a raw frame. It is an array of integers values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form 0xf).forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"canFrameCommand": [
{
"name": "iso-obd-010d",
"ecu": "engine_ecu",
"data": [ 2, 1, 13 ]
}
]
}
Used to send CAN frames via Iso-TP protocol.
Fields description
name
: the name of the command, will be later used by actions.ecu
: the name of the ecu that is described in ecu description.data
: the data to send, as the CAN payload (without the length byte). It is an array of integer values. Goes up to 7 bytes. Can be decimal or hexadecimal (in the form "0xf").forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"canCommand": [
{
"name": "command_rpm",
"ecu": "engine_ecu",
"data": [ 1, 12 ]
},
{
"name": "command_vin",
"ecu": "engine_ecu",
"data": [ "0x09", "0x02" ]
}
]
}
Fields description
name
: the name of the command, will be later used by actions.ecu
: the name of the ecu that is described in ecu description.data
: as the CAN payload (without the length byte). It is an array of integer values. Goes up to 7 bytes. Can be decimal or hexadecimal (in the form "0xf").forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"tp2Command": [
{
"name": "command_vin",
"ecu": "engine_ecu",
"data": [ 9, 2 ]
}
]
}
Used to send CAN frames via GMLAN protocol.
Fields description
name
: the name of the command, will be later used by actions.ecu
: the name of the ecu that is described in ecu description. ECU must be of type "GMLAN".data
: the data to send, as the CAN payload (without the length byte). It is an array of integer values. Goes up to 7 bytes. Can be decimal or hexadecimal (in the form "0xf").forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object
with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in
the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"gmlanCommand": [
{
"name": "command_gmlan",
"ecu": "ecu_gmlan",
"data": [ 1, 12 ]
}
]
}
Fields description
name
: Mandatory. The name of the command, will be later used by actions.ecu
: Optional if you use standard KLine. The name of the ECU associated with the command, if any. Ignored if raw
is set to true
.defaultReplyTimeOutMS
: Optional, default value is 100 (ms). The timeout before hanging up if no answer received. It is a long int in milliseconds. It can vary between 50 and 10000 ms.raw
: Optional, default to false
. Indicates if the data
array must be interpreted as raw. See raw
interpretation differences for each following parameter.data
: Mandatory. Data to send as a bytes array. Bytes must be represented with decimal integers or with hexadecimal strings like "0xF"
. If raw
parameter is not set or set to false
, the array represents the message's payload, and the maximum array size is of 256 bytes. Else, if raw
parameter is set to true
, the array represents the whole frame, and the maximum array size is of 261 bytes.headerBytes
: Optional, default is 0. Used in case of multi-frame messages. Number of heading bytes to chop from each frame. If raw
is set to false
the KLine headers are not took into account, choping starting from the first KLine payload byte. Else, if raw
is set to true
KLine headers are took into account, chopping starting from the first frame byte.checksumBytes
: Optional, default is 0. Number of checksum bytes to chop from each frame. Ignored if raw
is set to false
.ecuByteIndex
: Optional, default to -1, which means not used. This value represents the index of the ECU identifier byte. Used to process received responses from only one ECU. Ignored if raw
is set to false
.sequenceByteIndex
: Optional, default to -1, which means not used. This value represents the index of a sequence byte in the KLine message, to check for good sequence in case of multiframe messages. If raw
is set to false
the index starts from the first KLine payload byte. Else, if raw
is set to true
the index starts from the first frame byte.checksum
: Optional, default is -1, which means not used. If used, the value represents an integer in the range [0,255]. If not used, the value is automatically computed by lower-level layers. Used to force own checksum in the sent KLine command. Ignored if raw
is set to true
.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"klineCommand": [
{
"name": "command_rpm",
"data": [ 1, 12 ],
"checksum": 201
},
{
"name": "command_vin",
"data": [ 9, 2 ],
"defaultReplyTimeOutMS": 100,
"headerBytes": 3,
"sequenceByteIndex": 2
},
{
"name": "command_rpm_non_standard",
"ecu": "kline_engine_ecu",
"data": [ 1, 12 ]
},
{
"name": "command_rpm_raw",
"raw": true,
"data": ["0xC2", "0x33", "0xF1", "0x01", "0x0C", "0xF3"],
"ecuByteIndex": 2,
"checksumBytes": 1,
"defaultReplyTimeOutMS": 200
},
{
"name": "command_vin_raw",
"raw": true,
"data": ["0xC2", "0x33", "0xF1", "0x09", "0x02", "0xF1"],
"headerBytes": 6,
"checksumBytes": 1,
"sequenceByteIndex": 5,
"defaultReplyTimeOutMS": 200
}
]
}
Fields description
name
: the name of the command, will be later used by actions.defaultReplyTimeOutMS
: The default value is 100 (ms). The timeout before hanging up if no answer received. It is a long int in milliseconds. It can vary between 50 and 10000 ms.data
: the data to send. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xf").headerBytes
: number of header bytes in the payload of the J1850 message (not counting the J1850 headers themselves). Used in case of multiframe messages.sequenceByteIndex
: index of a sequence byte in the payload of the J1850 message, to check for good sequence in case of multiframe messages.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"j1850Command": [
{
"name": "command_rpm",
"data": [ 1, 12 ]
},
{
"name": "command_vin",
"data": [ 9, 2 ],
"defaultReplyTimeOutMS": 100,
"headerBytes": 3,
"sequenceByteIndex": 2
}
]
}
Fields description
name
: the name of the command, will be later used by actions.pgnNumber
: the number of the requested PGN.spnMask
: mask corresponding to the requested SPN.srcAddress
: this parameter is optional. If set to a positif integer, srcAddress of the ECu that answered will be checked before treating the answer.mode
: broadcast or request.interface
: the name of the interface. Default: can0.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"j1939Command": [
{
"name": "SPN_190",
"pgnNumber": "61444",
"spnMask": "FFFF000000",
"srcAddress": 0,
"mode": "broadcast",
"interface": "can0"
},
{
"name": "PGN_65244",
"pgnNumber": "65244",
"spnMask": "",
"mode": "request",
"interface": "can0"
}
]
}
Fields description
name
: the name of the command, will be later used by actions.mid
: the MID of the command.data
: the data to send after the MID.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in
the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"j1708Command": [
{
"name": "MID_45",
"mid": "45",
"data": [ 9, 2 ]
}
]
}
Fields description
name
: the name of the command, will be later used by actions.pid
: the PID of the command.mid
: this parameter is optional. If set to a positive value, the mid of the answer will be checked before treating the command.mode
: broadcast or request.forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.
{
"j1587Command": [
{
"name": "PID_45",
"pid": "45",
"mode": "broadcast"
},
{
"name": "PID_45",
"pid": "45",
"mid": 128,
"mode": "broadcast"
}
]
}
Note: the sleep commmand does not send any data to the device.
name
: the name of the command, will be later used by actions.sleepTimeMs
: time to wait in the sleep.
{
"sleepCommand": [
{
"name": "Sleep500Ms",
"sleepTimeMs": 500
}
]
}
Any command that uses the "data
" array field can be used as a parameterized command. A parameterized command is a command that depends on the result of another command.
Notes:
return
field).parameterized_command
in the example).parameterized_command
and parameterized_command_2
: the latter will always send three bytes, the former will send only two bytes if RPM is < 256.Example code:
{
"canCommand": [
{
"name": "command_rpm",
"ecu": "engine_ecu",
"data": [ 1, 12 ]
},
{
"name": "parameterized_command",
"ecu": "engine_ecu",
"data": [
1,
"command_rpm[2]*256+command_rpm[3]"
]
},
{
"name": "parameterized_command_2",
"ecu": "engine_ecu",
"data": [
1,
"command_rpm[2]",
"command_rpm[3]"
]
}
],
"actionList": [
{
"name": "my_action",
"depends": [
"command_rpm",
"parameterized_command",
"parameterized_command_2"
],
"return": "0"
}
]
}
Any command that uses the "data
" array field can be used as a parameterized command with a command of variable length result. A parameterized command with a command of variable length result is a command that depends on the result with variable length of another command.
Notes:
return
field).parameterized_command
in the example).Example code:
{
"canCommand": [
{
"name": "ReportDTCByStatusMask",
"ecu": "engine_ecu",
"data": [
"0x19",
"0x02",
"0xFF"
]
},
{
"name": "ReportDTCSnapShot",
"ecu": "engine_ecu",
"data": [
"0x19",
"0x04",
"ReportDTCByStatusMask_Pattern[0]",
"ReportDTCByStatusMask_Pattern[1]",
"ReportDTCByStatusMask_Pattern[2]",
"0xff"
]
},
{
"name": "ReportDTCExtData",
"ecu": "engine_ecu",
"data": [
"0x19",
"0x06",
"ReportDTCByStatusMask_Pattern[0]",
"ReportDTCByStatusMask_Pattern[1]",
"ReportDTCByStatusMask_Pattern[2]",
"0xff"
]
}
],
"actionList": [
{
"name": "doReportDTCDataForAll",
"depends": [
"ReportDTCByStatusMask"
],
"loop": {
"depends": [
"ReportDTCExtData",
"ReportDTCSnapShot"
],
"target": "ReportDTCByStatusMask",
"patternLength": 4,
"startOffset": 3
},
"report": "all",
"return": 0
}
]
}
It is not a real command, but is used to register to ECUs in broadcast mode. Must be used with listen-mode actions.
Fields description
name
: the name of the command, will be later used by actions.ecu
: the name of the ecu to listen to.mask
: (optional) mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filter
: (optional) array of arrays of integer values (same format as mask
). Used to filter frames that you want to listen from the ECU. See explanation below.throttlePeriodMs
: (optional) throttle the received message rate to this period (in ms).
forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.mask
and filter
usage
Let us begin by an example. You want to listen to the RPM frames from the engine ECU. You can write:
{
"canFrameReceive": [
{
"name": "listen_rpm",
"ecu": "engine_ecu",
"mask": ["0x00", "0xFF", "0xFF"],
"filter": [
["0x00", "0x41", "0x0C", "0xFF", "0xFF"]
],
"throttlePeriodMs": 1000
}
]
}
The mask
is set to the second and third bytes of the payload. The filter is "41 0C" on these two bytes: it is the static part of the frame, common to all RPM frames. Then, the "0xFF" on bytes 4 and 5 of the filter are the bits to watch for new data. If two consecutive frames sent by the ECU are identical regarding these two bytes (= if the RPM is the same), the second frame will not be treated.
Now if we also want to watch the speed, we need to update the filter to :
{
"filter": [
["0x00", "0x41", "0x0C", "0xFF", "0xFF"],
["0x00", "0x41", "0x0D", "0xFF"]
]
}
(OBD Speed is on only 1 byte, RPM is on two bytes).
If you want to get all frames from an ECU, you don't need to specify the mask
and filter
:
{
"canFrameReceive": [
{
"name": "listen",
"ecu": "engine_ecu"
}
]
}
Note: in this scenario, only the dstId
of the ECU is used, not the srcId
.
As CanFrameReceive, CanPolling commands are only listening to the CAN bus. They are more suited for data that change all the time (wheel speed etc.), whereas CanFrameReceive are more suited to listen to event-based data (ignition, door or lamp status, etc.).
They must be used with listen mode actions.
Fields description
name
: the name of the command, will be later used by actions.ecu
: the name of the ecu to listen to.mask
: (optional) mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filter
: (optional) array of arrays of integer values (same format as mask
). Used to filter frames that you want to listen from the ECU. See explanation below.throttlePeriodMs
: (optional) throttle the received message rate to this period (in ms).
forbiddenRawFilters
: (optional) A JSON Array of raw answers that must be filtered. All the elements of the Array must be JSON Object with the following fields:
mask
: mask on which to apply the filters. It is an array of integer values. Goes up to 8 bytes. Can be decimal or hexadecimal (in the form "0xff").filters
: array of arrays of integer values (same format as mask
). Used to filter answers that you want to drop. If a raw data answer matches on the mask/filter combination, the answer will not be treated.mask
and filter
usage: see CanFrameReceive
.
{
"canPolling": [
{
"name": "rec_123",
"ecu": "ecu_123",
"throttlePeriodMs": 100
}
}
Note: in this scenario, only the dstId
of the ECU is used, not the srcId
.
For internal use only.
Expressions are small Java classes that implement a specific interface understood by the ObdStacks code on the device, and can be loaded to perform advanced calculations on frames.
name
: the full class name.data
: the class data (base64-encoded dex file).
{
"expressionDefinition": [
{
"name": "com.example.MyClass",
"data": "..."
}
]
}
Actions allow to to do some calculation on the result of commands and other actions, and were designed using the model of ant
targets.
There are two types of actions, distinguished by the mode
parameter: either request
(default) or listen
. request
actions depend on commands with data bytes to actually send, whereas listen
actions depend on passive commands (like canFrameReceive
). Both types of actions have specific parameters.
MANDATORY fields
name
: The name of the action.return
: It is a double
. The return
field contains an arithmetical expression that will be used to compute the action's result. It is based on the exp4j
library.
double
values
(+
, -
, *
, /
) as well as more advanced operations
(abs
, sin
, cos
, ...). For the complete list of
available operations, please refer to:
http://www.objecthunter.net/exp4j/index.html and to the
Return and formula fields paragraph below.names
that were declared in your dependencies
. If they were
not declared, your description file won't even compile when
sent to the device.OBD_010D[0]
, or
((OBD_0110[0] * 256) + OBD_0110[1]) / 100
.DB_<DB_NAME>
(for example, DB_MDI_OBD_RPM
). It
will use the current value of the DB at the time the result
is computed.returnExpression
: can be used in place of return
field. See below section Custom Expressions.initSession
, communication
, closeSession
:
this structure allows you to define 3 lists of
actions/commands. If it fails the initSession
will be
executed again up to initAttempts
times, and each
retry will be delayed by initDelay
. The
communication
session is the core of the action, it is
the main work to execute. If one of the dependencies
execution fails, then the session is interrupted. The
closeSession
should always be executed, without regard
to the communication
execution success. . They are of
the form:
"communication":["speedKmPerHour"]
: The
command/action called speedKmPerHour
will be
executed when this action is called.before
the line they are called.depends
: It has the same form as the previously
mentioned fields. We recommend the use of the other
structure over this one, as it is more modular.initAttempts
: Maximum number of retries for the init
session. Default value is 1. Use only if there'sinitDelay
: Delay in ms between two successive attempts of
initSession
execution. Default value is 500ms.OPTIONAL fields common to all types of actions
exportToDB
: DB field where the result of the action will
be saved to each time it is executed. It allows easy reporting
in tracking or easy use in user application. You can also
specify the type of the result you want to store in the DB by
appending ":X"
, with X being one of the following: D
: double
(default), I
: int, X
: hexadecimal value (example:
"MY_DB:I"
).record
: tracking field to record the result of the action
(without going through DB). Useful to send the result when there
is no need to store it.returnType
: the return type of the action. Possible
values: string or double. Defaults to double.exports
: array of other formula/db pairs to export more
than one result of an action, if needed.
formula
: the corresponding formula. Same syntax as the
"return" field.expression
: the corresponding expression (can be used
instead of formula
). Same syntax as
returnExpression
.db
: the name of the db field to export to (with the
optional type, same syntax as exportToDB
.record
: tracking field to record the result of the
formula (without going through DB). Useful to send the
result when there is no need to store it.mode
: either request
(default) or listen
.
Listen mode must be specified when using
canFrameReceive
or canPolling
as a dependency.accumulator
: An accumulator aims to support cyclic
counters, that are counters on a fixed number of bits that
overflow periodically. Instead of returning the counter value,
it will return a value accumulated (incremented) over time.
Expression defined in the return
/ returnExpression
must be the payload data. No conversion should be included in
it. Use setpMultiplier
instead.
counterMaxValue
(mandatory): unsigned integer value,
mandatory as soon as an accumulator
object is defined.
Used to define the interval of the accumulator values:
[0; $counterMaxValue]
. The max value specified is
included in the range. These values are raw, they do not
include the stepMultiplier
(see next line) factor.stepMultiplier
(optional): floating value, defaults to
1.0
. Factor applied to the accumulator value. Use case
example: for an accumulator representing the fuel
consumption, let's say that one accumulator's step (one
unit) represents 0.25 µL of fuel, apply a
stepMultiplier
of 0.25
to retrieve directly the
fuel consumption instead of the raw accumulator value.OPTIONAL fields specific to "request" mode
EXECUTION
periodSec
: It is an integer. When declaring an action,
the user will be able to schedule its execution at a
specific period. If set to 0 (default value), disables it ;
otherwise, it repeat the action every periodSec
seconds. Please, don't mixed up with an execution
command of the same action, as this will degrade
performances. A first execution is already done when loading
the stack. Don't use too short periods if reporting to the
CC is enabled since this will lead to data drops.connectionState
: Integer, execute the action only in a
specific connection state. 1: only if we are connected to
OBD, 0: only if we are not, -1 (default): always.ignitionState
: Integer, execute the action only in a
specific ignition state. 1: only when ignition is on, 0:
only when ignition is off, -1 (default): always.movementState
: Integer, execute the action only if the
vehicle has moved (the vehicle is consider to have moved if
the speed is bigger than a certain paramterable threshold,
5km/h by default). 1: only when vehicle has moved, 0: only
when vehicle do not moved (ie speed is 0km/h), -1 (default):
always.passiveState
: Integer, execute the action only in a
specific passive mode state. 1: only if the passive mode is
on, 0: only if the passive mode is off, -1 (default) always.
Be aware : when setting the passiveState to 1, the action
will be executed in listen-only. Make sure that the desired
value is broadcasted on the bus.maxErrors
: Integer, stop executing the (periodic)
action after this number of failures (and until the next
reboot). If you use this parameter it is highly recommended
to use connectionState
, ignitionState
or
passiveState
in conjunction with it, so that the
action is executed only when it has a chance to succeed.
Note: maxErrors
applies only on the failure of the
return
formula computation, not on the additional
db
/ formula
pairs in the exports
parameter.REPORTING
report
:
yes
: The result of this action will be sent to
server each time it is executed.all
: The result of this action along with its
dependencies will be sent to server each time it is
executed. if a loop field is present, all the commands
of the loop will be reported too with the following
nomenclature in the example described in the loop field:
CommandB_DTC1, CommandB_DTC2, ..., CommandB_DTCn with
DTCx representing by their bytes in hexa. For example if
DTC1 is 0x0A 0x9B 0x17 with status 0x24 (ie the response
of CommandA is "0x59 0x02 0x7F DTC1 (="0x0A 0x9B 0x17
0x24") DTC2 ... DTCn" there will be, in the report, a
CommandB_0A9B1724.serverParameters
: A string that will be given back
along the results.PARAMETERIZED ACTIONS
loop
: It is a JSON object. This field is used to
proceed one or more parameterized commands which have a
parameter that depends on a variable length response of a
command. For example you may want to do the following
procedure. Send a command commandA to ask the DTCs available
for an ECU. Take the response and extract the different DTCs
available. For each DTC send a command commandB (which will
obviously be parameterized with the bytes representing the
DTC). This procedure is possible with the loop option with
the following mandatory
fields:
depends
: JSON array with all the commands you want
to execute with the "pattern" response of the
target
command. In the example previously
described, depends
would be "commandB", target
"commandA" and the pattern the DTC. Also, for all the
commands of this field, if you want to use bytes of the
pattern, you must use this nomenclature:
"CommandA_Pattern". In the example previously
described, the DTCs are representing with 4 bytes in the
response of the commandA: 3 bytes for the DTC identifier
and 1 byte of status. So, in commandB, you will find
"CommandA_Pattern[0]", "CommandA_Pattern[1]" and
"CommandA_Pattern[2]" to send the command for the
right DTC for each loop step.target
: the name of THE command from which you
want to extract the information to import in the
depends
field of the loop. In the example
previously described target would be commandA.patternLength
: the length of the pattern to
extract in the result of the target command. In the
example previously described patternLength would be 4
(each pattern is 3 bytes for the DTC identifier + 1 byte
for the status).startOffset
: the offset from the start of the
response to start the loop. In the example previously
described, if the response of commandA is "0x59 0x02
0x7F DTC1 DTC2 ... DTCn", startOffset would be 3, the
first pattern to put in the loop starts at byte 3 of the
response. Note: startOffset
starts the count
at the command payload, for example, when doing ISO
15765-4, the count starts after the length byte.OPTIONAL fields specific to listen mode
startListenOnLoad
: If set to false
, when loading the
stack, don't start listening at once and wait for an
executeAction
request before doing so. Default:
true
.polling
: register this action to the PollingManager. This
allows retrieving the action's results through the PollingClient
interface. Note: this parameter only works when used with
canPolling
commands.Available operations
The basic mathematical operations available are listed on
http://www.objecthunter.net/exp4j/index.html
Along with this list, some other operations can be used:
&
and |
. Example: "CAN_FRAME[0] & 8"
. This operation
works only on a byte and not on the complete frame."CAN_FRAME[0] & 0x08"
getInt(data, offset, length)
,
getIntS(data, offset, length, signed)
,
getIntSE(data, offset, length, signed, endianness)
data
: the full frame on which to parse the int.offset
: the offset in bitslength
: number of bitssigned
: 0: unsigned, 1: signed. Default is 0endianness
: 0: big endian, 1: little endian. Default is 0getIntSE(CAN_FRAME, 8, 12, 1, 0)
: get a signed
integer from CAN_FRAME
which is on 12 bits with an offset of 1
byte in big endian format.==
, !=
, >
, <
, >=
, <=
. The
result of these operators is 0 (false) or 1 (true) (as a double). To
use the result in DB as a boolean, use the integer type (":I"
)
inside the DB.&&
and ||
. The result of these operators is 0 (false) or
1 (true) (as a double). To use the result in DB as a boolean, use
the integer type (":I"
) inside the DB.The custom expressions can be used instead of the return
formulas.
The advantage is a much higher performance and efficiency, but the
number of operations is limited.
List of available operations:
ParseInt
Works only with actions that have a single dependency frame.
Allows to parse an integer (with optionnal sign and endianness) and make
linear calculation on it: Ax+B
parseInt(int bitOffset, int bitLength, boolean signed, boolean bigEndian, double valueFactor, double valueOffset)
bitOffset
: the offset in bits.bitLength
: the number of bits of the integer.signed
: should the result be interpreted as signed or unsigned
int (default: false).bigEndian
: boolean, false for little endian (default: true).valueFactor
: multiplicator for the final result (A
in
Ax+b
) (default: 1).valueOffset
: offset for the final result (B
in Ax+b
)
(default 0).
{
"name": "ParseInt",
"parameterTypes": [ "int", "int", "boolean", "boolean", "double", "double" ],
"parameterValues": [ 0, 16, false, true, 2, 5 ]
}
There also exists simpler variations of the API:
parseInt(int bitOffset, int bitLength, boolean signed, boolean bigEndian)
{
"name": "ParseInt",
"parameterTypes": [ "int", "int", "boolean", "boolean" ],
"parameterValues": [ 0, 16, false, true ]
}
parseInt(int bitOffset, int bitLength, double valueFactor, double valueOffset)
{
"name": "ParseInt",
"parameterTypes": [ "int", "int", "double", "double" ],
"parameterValues": [ 0, 16, 2, 5 ]
}
parseInt(int bitOffset, int bitLength)
{
"name": "ParseInt",
"parameterTypes": [ "int", "int" ],
"parameterValues": [ 0, 16 ]
}
ParseOneByte
Works only with actions that have a single dependency frame.
Allows to make quick computations on a single byte of a frame.
parseOneByte(int byteIndex, double valueFactor, double valueOffset)
byteIndex
: The byte index.valueFactor
: multiplicator for the final result (A
in
Ax+b
) (default: 1).valueOffset
: offset for the final result (B
in Ax+b
)
(default: 0).
{
"name": "ParseOneByte",
"parameterTypes": [ "int", "double", "double" ],
"parameterValues": [ 0, 2, 5 ]
}
parseOneByte(int byteIndex)
{
"name": "ParseOneByte",
"parameterTypes": [ "int" ],
"parameterValues": [ 0 ]
}
request
actions cannot depend on "listen commands"
(canFrameReceive
) and listen
actions cannot depend on
"active commands" (all other commands).canFrameReceive
command. Multi-dependency for these actions is
not possible for now.
{
"actionList": [
{
"exportToDB": "VEHICLE_SPEED_KM_H",
"name": "speedKmPerHour",
"depends": [
"OBD_010D"
],
"return": "OBD_010D[0]"
},
{
"exports": [
{
"formula": "OBD_010D[0]",
"db": "VEHICLE_SPEED_KM_H2"
}
],
"name": "speedKmPerHour2",
"depends": [
"OBD_010D"
],
"return": "0"
},
{
"periodSec": 60,
"report": "all",
"name": "diagnostics",
"depends": [
"speedKmPerHour",
"maf",
"literPerSec",
"literPer100Km"
],
"return": "0"
},
{
"name": "listenAction",
"mode": "listen",
"depends": [
"broadcasted_frame"
],
"return": "broadcasted_frame[0]*256+broadcasted_frame[1]"
},
{
"name": "doReportDTCDataForAll",
"depends": [
"ReportDTCByStatusMask"
],
"loop": {
"depends": [
"ReportDTCExtData",
"ReportDTCSnapShot"
],
"target": "ReportDTCByStatusMask",
"patternLength": 4,
"startOffset": 3
},
"report": "all",
"return": 0
},
{
"name": "requestDataInSession",
"initSession": [
"commandInitSession"
],
"communication": [
"dataRequest1",
"dataRequest2"
],
"closeSession": [
"commandCloseSession"
],
"initAttempts": 3,
"initDelay": 500,
"return": 0
},
{
"name": "accumulatePeriodicFuelConsumption",
"mode": "listen",
"depends": [
"fuelConsumedPeriodicFrame"
],
"accumulator": {
"counterMaxValue": 255,
"stepMultiplier": 0.25
},
"returnExpression": {
"name": "ParseOneByte",
"parameterTypes": [
"int"
],
"parameterValues": [
0
]
}
}
]
}
To retrieve the results of the execution of the OBDStacks command, you have to:
When a command is executed ( periodically with "periodSec" or through a message sent by an API command or by the deviceManager ) a mesage will be sent by webhook. This message is described below :
stackStatus
: it is an integer that indicates if the stack is
operational. 1 means OK or loaded properly or dropped properly, 0
action couldn't be performed on this stack.name
: A string that is the name of the current stack.results
: It is a JSON
array that contains the list of
results per action.
actionListName
: The name of the executed action.serverParameters
: The value of serverParameters present in
the executed actionList command. If not present or empty/NULL in
actionList, it won't be send back to server.result
: an double
that is the result of the
calculation of the expression described in result
from the
actionList.resultList
: a JSON
array that contains bytes from
all dependancies of the executed actionList if the optional
report
attribute is set to all
.
commandName
: The command namedata
: An array of integers that were returned by this
command{
"results": [
{
"actionListName": "speedKmPerHour",
"result": 255
},
{
"actionListName": "EcuId",
"serverParamters": "version3",
"result": 0,
"resultList": [
{
"commandName": "w7E0_3E00",
"data": [
127,
62
]
},
{
"commandName": "w7E0_3E01",
"data": [
127,
32,
18
]
}
]
}
]
}
Make sure that your device has the app Advanced CAN Gateway binded (http://www.munic.io/documentations/how_to_link_app). Then, you just have to use the app on the DM Apps page.
When associated, an "Apps" tab is available from your Morpheus Manager interface.
In the interface below, select the asset and paste the commands to load in the edition box. The session below describes the possible commands to load.
Clicking on "Save changes" will immediately send the contents of the edition box to the asset(s).
Finally, the results are sent by the device in the form of message packets, not track packets. See http://www.munic.io/documentations/tracks#toc_2 for the documentation on how to parse message packets.
JSON
OBDStackThe general documentation for sending messages using apps is here:
https://dashboard.munic.io/api_doc/v2/versions/send_app_messages.html
The app to use is Advanced CAN Gateway with id 52.
Example POST request (to request the availability of the action named readAllDTC):
POST '/api/v2/modules/versions/52/messages':
{
"targeted_assets": [ "351732XXXXX95", "351732057XXXX8" ],
"targeted_assets_group_ids" : [ 1, 2 ]
"messages": [ "{ \"request\": \"isActionAvailable\", \"name\": \"readAllDTC\" } ]
}
You can choose to use either targeted_assets
or targeted_assets_group_ids
to send the ObdStacks request to a list of assets or asset groups respectively.
drop
action is
called.name
.JSON
stack :
{
"request": "loadStack",
"requestId": "Stack",
"jsonString": {
"obdStack": { }
}
}
{
"stackStatus": 1,
"name": "stackAstackB"
}
if stack was correctly loaded, or
{
"stackStatus": 0
}
in case of error.
request
is a mandatory field. It tells the program which
kind of request it is. Use isActionAvailable for this type of
request.name
is a mandatory field. The name of the action you want
to check.requestId
is an optional field. If present, it will be
found in the answer from the program. It allow one to understand
to which request the answer is related.
{
"request": "isActionAvailable",
"name": "speedKmPerHour",
"requestId":"myinternalId"
}
{
"requestId":"myinternalId",
"name": "speedKmPerHour",
"available":true
}
request
is a mandatory field. It tells the program which
kind of request it is. Use executeAction to execute a stack
action.name
is a mandatory field. The name of the action to
execute. It must be present in the currently loaded stack.requestId
is an optional field. If present, it will be
found in the answer from the program. It allow one to understand
to which request the answer is related.
{
"request": "executeAction",
"name": "speedKmPerHour",
"requestId":"myinternalId"
}
{
"requestId":"myinternalId",
"results": [
{
"actionListName": "speedKmPerHour",
"result": 255,
}
]
}
request
is a mandatory field. It tells the program which
kind of request it is. Use executeAction to execute a stack
action.actions
is a mandatory field. The array of actions as a
valid action request - see previous "Execute an action".requestId
is an optional field. If present, it will be
found in the answer from the program with a dash followed by the
ID of the action. It allow one to understand to which request
the answer is related.
{
"request": "executeActions",
"actions": [
{
"request": "executeAction",
"name": "speedKmPerHour"
},
{
"request": "drop",
}
],
"requestId":"myinternalId"
}
{
"requestId":"myinternalId-1",
"results": [
{
"actionListName": "speedKmPerHour",
"result": 255,
}
]
}
Then a second message
{
"requestId":"myinternalId-2",
"drop": true,
"name": "my stack name"
}
All messages are added to the current stack. This allow you to send your
stack with several messages.
The stacks send to the message are saved on the flash of the device and
are retreive upon reboot.
Whenever an action, command, ecu has the same name as a previous one,
the new one replaces the old one.
Whenever a message contains the drop command, then all information from
RAM, Flash are dropped before handling the message itself.
The answer has the field drop
that indicates the status (true or
false) and when true, the field name
that contains the dropped
stack name (No name if name is not set).
{
"request": "drop"
}
{
"request": "drop",
"stackName": "MyStackName"
}
{
"drop": true,
"name": "my stack name"
}
if stack was correctly dropped, or
{
"drop": false
}
in case of error.
{
"request": "getName"
}
{
"name": "No Name"
}
{
"error": "Illegal argument: Action unknownAction doesn't exist"
}
JSON
: ""
.JSON
: -0.1
.You can get the current connection's configuration of a device thanks to
the following request.
You have the possibility to receive the connection's parameters from one
protocol only (CAN, KLine or J1850), or to get all of them on the same
request.
There is a description of its fields:
request
: a string which is "getConnectionParameter"protocol
(optional
): Specify the protocol you want the
parameters. This field is a string, which can be filled with either
"can", "kline", "j1850" or "all". By default, the informations about
every protocol will be sent.The response will be:
getConnectionParameter
: a JSON Object which contain the same
JSON
Object as the one called "configuration" bellowSome examples:
{
"request": "getConnectionParameter"
}
Response:
{
"getConnectionParameter": {
"active": true,
"connectionInfo": [{
"listenOnly": false,
"canBaudRate": 424242,
"canConnection": "CAN-OBD-TEST"
}, {
"type": "j1850",
"ifr": 42,
"srcAddress": 42,
"mode": 0
}]
}
}
And:
{
"request": "getConnectionParameter",
"protocol": "j1850"
}
Response:
{
"getConnectionParameter": {
"active": true,
"connectionInfo": [{
"type": "j1850",
"ifr": 42,
"srcAddress": 42,
"mode": 0
}]
}
}
This section describes the non-usual case when you want to set a
specific configuration with a setConnections
request.
This is only used to access proprietary buses but is not necessary to
access standard buses.
Warning : except for CAN, setConnections
is only available on 3.04029XXX and more
There is a description of it's fields:
request
: a string which is "setConnections"configuration
: It is a JSON
object that contains :
active
: a boolean to indicate if you want to activate the
connection after setting the configuration.pinSwitchPeriodMS
(optional
) (for Can
connections only) : the period of the PIN switch mode which will
be enable if you chose to fill this field.connectionInfo
: It is a JSON
array with the
different informations of the different connections you want to
set.
type
: The type of connection. Possibilities are "can",
"kline", "j1850". If not set, type will be "can".CAN related options
canConnection
(mandatory
): Specify the bus
to use (contact us for details about CAN PIN switching
capabilities).canBaudRate
(mandatory
): Specify the speed
of the bus if you want to restrict it. Common values are
250000 or 500000.listenOnly
(optional
): If set to true, the
Can connection will be full listen only, nothing will be
send on the bus, the connection will only listen the
bus. if not set this option will be set to falseKLine related options, all OPTIONAL
default_configuration
: Json object used to
set the default values of the connections
parameters.configs
: Json array used to store jsonObject
that defines connection parameters.initList
: Store two value. a config name
("config"), and a number of tries ("tries"). It is
used to set a connection procedure.p1Max
: Inter-byte timing parameter of the
ECU, in 0.5 ms per unit.p3Min
: Min time between end of ECU response
and new tester request, in 0.5 ms per unit.p4Min
: Inter-byte timing parameter of the
tester, in 0.5 ms per unit.w1
: Time in ms from end of address byte to
start of synchronization pattern.w2
: Time in ms between synchronization
pattern and byte 1.w3
: Time in ms between key byte 1 and 2.w4
: Time in ms between key byte 2 and its
inversion from the client.w5
: Time in ms before client should transmit
address byte.tidle
: Tester idle time in ms.tinil
: Tester low time in ms.twup
: Tester wakeup time in ms.dataBits
: set this value to 1 if you want a 7
bits UART KLine. if not set the precedent value (or
the default value if no precedent) will be set.invertPolarity
: boolean value. Invert
everything on the bus, including the INIT sequence
and the messages.initKOnly
: boolean value. Only use the K-line
moves during initialization.initLOnly
: boolean value. Only use the L-line
moves during initialization.TXUseLLine
: boolean value. After the init, in
mode uart, the messages are sent using the L-line
instead of the K-line. Reception remains on the
K-Line.TXUseKAndL
: boolean value. After the init, in
mode uart, the messages are sent using the L-line
and the K-line. Reception remains on the K-Line.baudrate
: uint32 value. if not set the
precedent value (or the default value if no
precedent) will be set.parity
: uint16 value. if not set the
precedent value (or the default value if no
precedent) will be set.fivebaudMode
: uint16 value. if not set the
precedent value (or the default value if no
precedent) will be set.initType
: string value. Can be "SLOW", "FAST,
or "NONE".noCheckKeywords
: boolean value to indicate if
you want to check to keywords sent by the vehicle.
if not set the value will be false (ie keywords will
be checked).priorityISO9141
: boolean value. if
initType
has been set to "NONE", and
noCheckKeywords
is true, this parameter will
force one of the two kline protocols.pingPayload
: an array byte representing the
payload of a ping message. Used to keep the
connection alive.pingChecksum
: integer used to overload the
checksum of the frame used to ping.startCommunicationPayload
: an array byte
representing the payload of a message used to start
the connection. Only used for KWP2000 connections.startCommunicationChecksum
: integer used to
overload the checksum of the frame used to start
communication in KWP2000.J1850 related options
mode
: 0 for PWM, 1 for VWP, -1 to testing all
cases. if not set the field will be -1.srcAddress
: String of length 2 representing the
hexa source address for the connection. if not set the
address will be 0xF1 (same as if the field is set to
"F1").ifr
: String of length 2 representing the hexa ifr
message send by the device to acknowledge a message
during the connection. if not set the ifr will be 0xF1
(same as if the field is set to "F1").NOTE: for KLine
: if you set any of the field
initAddress
, initSrcAddress
or noCheckKeywords
you
MUST
use the filed ecu
in ALL
your klineCommand
(and, of course, have set "ecuDescription" of type "kline" before).
{
"request": "setConnections",
"requestId": "Connections",
"configuration": {
"active": true,
"connectionInfo": [
{
"type": "kline",
"ecuInitList": [
{
"name": "init_procedure_0",
"configs": [
{
"name": "init_config_0",
"baudrate": 5,
"initType": "SLOW"
},
{
"name": "init_config_1",
"baudrate": 10400,
"initType": "FAST"
}
],
"initList": [
{
"config": "init_config_0",
"tries": 1
},
{
"config": "init_config_1",
"tries": 2
}
]
},
{
"name": "init_procedure_1",
"raw": true,
"configs": [
{
"name": "init_config_0",
"baudrate": 5,
"initType": "SLOW",
"pingPayload": ["0xC1", "0x33", "0xF1", "0x3E", "0x23"],
"startCommunicationPayload": ["0x33"],
"tidle": 300,
"tinil": 25,
"twup": 50
},
{
"name": "init_config_1",
"baudrate": 10400,
"initType": "FAST",
"pingPayload": ["0xC1", "0x33", "0xF1", "0x3E", "0x23"],
"startCommunicationPayload": ["0xC1", "0x33", "0xF1", "0x81", "0x66"],
"w1": 300,
"w2": 20,
"w3": 20,
"w4": 25,
"w5": 300,
"tidle": 300,
"tinil": 25,
"twup": 50
}
],
"initList": [
{
"config": "init_config_0",
"tries": 1
},
{
"config": "init_config_1",
"tries": 2
}
]
}
]
}
]
}
}
{
"obdStack": {
"name": "Default_OBD",
"obdCommand": [
{
"name": "OBD_0101",
"mode": "01",
"pid": "01"
},
{
"name": "OBD_012F",
"mode": "01",
"pid": "2F"
},
{
"name": "OBD_0111",
"mode": "01",
"pid": "11"
},
{
"name": "OBD_0104",
"mode": "01",
"pid": "04"
},
{
"name": "OBD_010A",
"mode": "01",
"pid": "0A"
},
{
"name": "OBD_015C",
"mode": "01",
"pid": "5C"
},
{
"name": "OBD_RPM",
"mode": "01",
"pid": "0C"
},
{
"name": "OBD_SPEED",
"mode": "01",
"pid": "0D"
},
{
"name": "OBD_0144",
"mode": "01",
"pid": "44"
},
{
"name": "OBD_015E",
"mode": "01",
"pid": "5E"
},
{
"name": "OBD_0151",
"mode": "01",
"pid": "51"
},
{
"name": "OBD_010F",
"mode": "01",
"pid": "0F"
},
{
"name": "OBD_010B",
"mode": "01",
"pid": "0B"
},
{
"name": "OBD_0110",
"mode": "01",
"pid": "10"
},
{
"name": "OBD_014F",
"mode": "01",
"pid": "4F"
},
{
"name": "OBD_0150",
"mode": "01",
"pid": "50"
},
{
"name": "OBD_0105",
"mode": "01",
"pid": "05"
},
{
"name": "OBD_VIN",
"mode": "09",
"pid": "02"
}
],
"actionList": [
{
"name": "getRPM",
"depends": [
"OBD_RPM"
],
"exportToDB": "MDI_OBD_RPM:I",
"return": "((OBD_RPM[0]*256)+OBD_RPM[1])/4"
},
{
"name": "getVehicleSpeed",
"depends": [
"OBD_SPEED"
],
"exportToDB": "MDI_OBD_SPEED:I",
"return": "OBD_SPEED[0]"
},
{
"name": "getThrottlePosition",
"depends": [
"OBD_0111"
],
"exportToDB": "MDI_OBD_THROTTLE_POSITION:I",
"return": "OBD_0111[0]*100/255"
},
{
"name": "getFuelLevelInput",
"depends": [
"OBD_012F"
],
"exportToDB": "MDI_DASHBOARD_FUEL_LEVEL:I",
"return": "OBD_012F[0]*100/255"
},
{
"name": "getEngineLoad",
"depends": [
"OBD_0104"
],
"exportToDB": "MDI_OBD_ENGINE_LOAD:I",
"return": "OBD_0104[0]*100/255"
},
{
"name": "getFuelPressure",
"depends": [
"OBD_010A"
],
"exportToDB": "MDI_OBD_FUEL_PRESSURE:I",
"return": "3*OBD_010A[0]"
},
{
"name": "getEngineOilTemperature",
"depends": [
"OBD_015C"
],
"exportToDB": "MDI_OBD_ENGINE_OIL_TEMP:I",
"return": "OBD_015C[0]-40"
},
{
"name": "getCER",
"depends": [
"OBD_0144"
],
"exportToDB": "MDI_OBD_CER:D",
"return": "(OBD_0144[0]*256+OBD_0144[1])*2/65535"
},
{
"name": "getFuelRate",
"depends": [
"OBD_015E"
],
"exportToDB": "MDI_OBD_FUEL_RATE:D",
"return": "((OBD_015E[0]*256)+OBD_015E[1])*0.05/3600"
},
{
"name": "getMAF",
"depends": [
"OBD_0110"
],
"exportToDB": "MDI_OBD_MAF:D",
"return": "((OBD_0110[0]*256)+OBD_0110[1])/100"
},
{
"name": "getIAT",
"depends": [
"OBD_010F"
],
"exportToDB": "MDI_OBD_IAT:D",
"return": "OBD_010F[0]-40"
},
{
"name": "getMAP",
"depends": [
"OBD_010B"
],
"exportToDB": "MDI_OBD_MAP:D",
"return": "OBD_010B[0]"
},
{
"name": "getEngineCoolantTemperature",
"depends": [
"OBD_0105"
],
"exportToDB": "MDI_OBD_ENGINE_COOLANT_TEMP:I",
"return": "OBD_0105[0] - 40"
},
{
"name": "getCERScale",
"depends": [
"OBD_014F"
],
"exportToDB": "MDI_OBD_CER_SCALE:D",
"return": "OBD_014F[0]/2"
},
{
"name": "getMAFScale",
"depends": [
"OBD_0150"
],
"exportToDB": "MDI_OBD_MAF_SCALE:D",
"return": "OBD_0150[0]*1000/65535"
},
{
"name": "getFuelType",
"depends": [
"OBD_0151"
],
"exportToDB": "MDI_OBD_FUEL_TYPE:I",
"return": "OBD_0151[0]"
},
{
"name": "getMonitorStatus",
"depends": [
"OBD_0101"
],
"exportToDB": "MDI_OBD_MONITOR_STATUS:I",
"return": "getInt(OBD_0101, 0, 32)"
},
{
"name": "getVIN",
"depends": [
"OBD_VIN"
],
"returnType": "string",
"return": "OBD_VIN"
}
]
}
}