Utworzenie logicznego kanału komunikacji na bazie połączenia fizycznego
Ostatnia zmiana:
Funkcja tworzy logiczny kanał komunikacji z pojazdem na wskazanym urządzeniu pass-thru. Kanał logiczny nakłada dodatkowy schemat protokołu na istniejący fizyczny kanał komunikacji.
Po pomyślnym wykonaniu funkcja zwraca STATUS_NOERROR, a wartość wskazywana przez pChannelID jest używana jako deskryptor (handle) utworzonego kanału. Kanał znajduje się w stanie zainicjalizowanym.
Dla jednego fizycznego kanału komunikacji dopuszczalnych jest do 10 kanałów logicznych. Utworzenie kanału logicznego nie wpływa na działanie kanału fizycznego ani innych powiązanych z nim kanałów logicznych.
long PassThruLogicalConnect(
unsigned long PhysicalChannelID,
unsigned long ProtocolID,
unsigned long Flags,
void *pChannelDescriptor,
unsigned long *pChannelID
)
Utworzony kanał logiczny ma następujący stan początkowy:
Parametr wejściowy. Identyfikator kanału fizycznego uzyskany podczas wywołania PassThruConnect().
Parametr wejściowy. Identyfikator protokołu dla logicznego kanału komunikacji. Określa, jak kanał logiczny będzie współpracować z pojazdem, a także typ struktury pChannelDescriptor.
| ProtocolID | Opis |
|---|---|
ISO15765_LOGICAL |
ISO 15765-2 ze sterowaniem przepływem (flow control) |
Parametr wejściowy. Flagi konfiguracji kanału logicznego. Flagi można łączyć przez OR.
| Flaga | Opis | Wartości |
|---|---|---|
FULL_DUPLEX |
Tryb dupleksu kanału. Tylko dla ISO 15765. | 0 = półdupleks 1 = pełny dupleks |
ISO15765_ON_J1939 |
Maskowanie bitów priorytetu (28-26) w CAN ID dla wiadomości ISO 15765 z 29-bitowym identyfikatorem (zgodnie z ISO 15765-2 Annex A oraz SAE J1939-21). Tylko dla ISO 15765. | 0 = maskowanie wyłączone (standardowa obsługa ISO 15765) 1 = maskowanie włączone |
Parametr wejściowy. Wskaźnik na strukturę opisującą punkty końcowe połączenia logicznego. Jeśli wskaźnik wynosi NULL, funkcja zwróci ERR_NULL_PARAMETER.
Parametr wejściowy. Wskaźnik na zmienną unsigned long przydzieloną przez aplikację. Po pomyślnym wykonaniu zmienna będzie zawierać identyfikator kanału logicznego do późniejszych wywołań funkcji.
Dla protokołu ISO15765_LOGICAL używana jest struktura ISO15765_CHANNEL_DESCRIPTOR, która definiuje punkty końcowe połączenia logicznego:
typedef struct {
unsigned long LocalTxFlags; // TxFlags dla LocalAddress
unsigned long RemoteTxFlags; // TxFlags dla RemoteAddress
unsigned char LocalAddress[5]; // CAN ID + extended address (strona lokalna)
unsigned char RemoteAddress[5]; // CAN ID + extended address (strona zdalna)
} ISO15765_CHANNEL_DESCRIPTOR;
Dozwolone flagi dla deskryptora kanału ISO 15765:
| Flaga | Zastosowanie | Opis |
|---|---|---|
CAN_29BIT_ID |
LocalAddress, RemoteAddress | Użyj 29-bitowego CAN ID (zamiast 11-bitowego) |
ISO15765_ADDR_TYPE |
LocalAddress, RemoteAddress | Użyj adresowania rozszerzonego (extended address) |
ISO15765_FRAME_PAD |
RemoteAddress | Włącz dopełnianie (padding) ramek flow control przy nadawaniu |
Address[0] — CAN ID bity 28-24 (trzy najstarsze bity muszą być zerowe)Address[1] — CAN ID bity 23-16Address[2] — CAN ID bity 15-8Address[3] — CAN ID bity 7-0Address[4] — adres rozszerzony (jeśli podano flagę ISO15765_ADDR_TYPE)LocalAddress i RemoteAddress muszą być unikalne. Żaden z adresów nie może być zgodny z adresami innych istniejących kanałów logicznych dla danego
kanału fizycznego. CAN ID z adresem rozszerzonym nie może być zgodny z CAN ID bez adresu rozszerzonego.
| Kod | Opis |
|---|---|
| STATUS_NOERROR | Funkcja wykonana pomyślnie |
| ERR_CONCURRENT_API_CALL | Funkcja J2534 API została wywołana przed zakończeniem poprzedniego wywołania |
| ERR_DEVICE_NOT_OPEN | PassThruOpen() nie został pomyślnie wywołany |
| ERR_INVALID_CHANNEL_ID | Niedozwolona wartość PhysicalChannelID |
| ERR_DEVICE_NOT_CONNECTED | Błąd komunikacji z urządzeniem pass-thru. Urządzenie zostało odłączone. |
| ERR_NOT_SUPPORTED | DLL nie obsługuje tej funkcji |
| ERR_LOG_CHAN_NOT_ALLOWED | Kanał logiczny nie jest dozwolony dla danej kombinacji kanału fizycznego i ProtocolID |
| ERR_PROTOCOL_ID_NOT_SUPPORTED | Wartość ProtocolID nie jest obsługiwana (niedozwolona lub nieznana) |
| ERR_FLAG_NOT_SUPPORTED | Wartości Flags są niedozwolone, nieznane lub niemające zastosowania dla bieżącego kanału |
| ERR_INVALID_CHANNEL_DESCRIPTOR | Jeden lub więcej elementów struktury pChannelDescriptor jest niedozwolony lub niemający zastosowania dla bieżącego kanału |
| ERR_NULL_REQUIRED | Parametr, który powinien być NULL, nie został ustawiony na NULL |
| ERR_NULL_PARAMETER | Przekazano wskaźnik NULL zamiast wymaganego wskaźnika |
| ERR_NOT_UNIQUE | Próba utworzenia kanału logicznego z adresami dublującymi adresy istniejącego kanału |
| ERR_EXCEEDED_LIMIT | Przekroczono maksymalną liczbę kanałów logicznych dla danego kanału fizycznego |
| ERR_FAILED | Nieokreślony błąd. Użyj PassThruGetLastError(), aby uzyskać opis. |
#include "j2534_dll.hpp"
unsigned long deviceID = 0;
unsigned long physicalChannelID = 0;
unsigned long logicalChannelID = 0;
// Otwieramy urządzenie
long ret = PassThruOpen("ScanDoc", &deviceID);
if (ret != STATUS_NOERROR) return;
// Tworzymy fizyczne połączenie CAN
ret = PassThruConnect(deviceID, CAN, CAN_29BIT_ID, 500000, &physicalChannelID);
if (ret != STATUS_NOERROR) {
PassThruClose(deviceID);
return;
}
// Konfigurujemy deskryptor kanału logicznego ISO 15765
ISO15765_CHANNEL_DESCRIPTOR channelDesc = {0};
// Adres lokalny (adapter) - 0x18DA00F1 (żądanie funkcjonalne)
channelDesc.LocalTxFlags = CAN_29BIT_ID;
channelDesc.LocalAddress[0] = 0x18;
channelDesc.LocalAddress[1] = 0xDA;
channelDesc.LocalAddress[2] = 0x00;
channelDesc.LocalAddress[3] = 0xF1;
// Adres zdalny (ECU) - 0x18DAF100 (odpowiedź z ECU)
channelDesc.RemoteTxFlags = CAN_29BIT_ID | ISO15765_FRAME_PAD;
channelDesc.RemoteAddress[0] = 0x18;
channelDesc.RemoteAddress[1] = 0xDA;
channelDesc.RemoteAddress[2] = 0xF1;
channelDesc.RemoteAddress[3] = 0x00;
// Tworzymy kanał logiczny
ret = PassThruLogicalConnect(
physicalChannelID,
ISO15765_LOGICAL,
0, // Flags: półdupleks
&channelDesc,
&logicalChannelID
);
if (ret == STATUS_NOERROR) {
printf("Kanał logiczny utworzony: %lu\n", logicalChannelID);
// Teraz można użyć logicalChannelID dla PassThruReadMsgs/PassThruQueueMsgs
// Zamykamy kanał logiczny
PassThruLogicalDisconnect(logicalChannelID);
}
// Zamykamy kanał fizyczny i urządzenie
PassThruDisconnect(physicalChannelID);
PassThruClose(deviceID);
from ctypes import *
# Ładowanie biblioteki
j2534 = cdll.LoadLibrary("libj2534_v05_00.dylib")
# Struktura deskryptora kanału
class ISO15765_CHANNEL_DESCRIPTOR(Structure):
_fields_ = [
("LocalTxFlags", c_ulong),
("RemoteTxFlags", c_ulong),
("LocalAddress", c_ubyte * 5),
("RemoteAddress", c_ubyte * 5)
]
device_id = c_ulong()
physical_channel_id = c_ulong()
logical_channel_id = c_ulong()
# Otwieramy urządzenie
ret = j2534.PassThruOpen(b"ScanDoc", byref(device_id))
if ret != 0:
print(f"Błąd PassThruOpen: {ret}")
exit()
# Tworzymy fizyczne połączenie CAN (500 kbit/s, 29-bit ID)
CAN = 0x05
CAN_29BIT_ID = 0x100
ret = j2534.PassThruConnect(device_id, CAN, CAN_29BIT_ID, 500000, byref(physical_channel_id))
if ret != 0:
print(f"Błąd PassThruConnect: {ret}")
j2534.PassThruClose(device_id)
exit()
# Konfigurujemy deskryptor kanału
ISO15765_LOGICAL = 0x200
ISO15765_FRAME_PAD = 0x40
channel_desc = ISO15765_CHANNEL_DESCRIPTOR()
channel_desc.LocalTxFlags = CAN_29BIT_ID
channel_desc.LocalAddress[0] = 0x18
channel_desc.LocalAddress[1] = 0xDA
channel_desc.LocalAddress[2] = 0x00
channel_desc.LocalAddress[3] = 0xF1
channel_desc.RemoteTxFlags = CAN_29BIT_ID | ISO15765_FRAME_PAD
channel_desc.RemoteAddress[0] = 0x18
channel_desc.RemoteAddress[1] = 0xDA
channel_desc.RemoteAddress[2] = 0xF1
channel_desc.RemoteAddress[3] = 0x00
# Tworzymy kanał logiczny
ret = j2534.PassThruLogicalConnect(
physical_channel_id,
ISO15765_LOGICAL,
0,
byref(channel_desc),
byref(logical_channel_id)
)
if ret == 0:
print(f"Kanał logiczny utworzony: {logical_channel_id.value}")
# ...praca z kanałem...
j2534.PassThruLogicalDisconnect(logical_channel_id)
else:
print(f"Błąd: {ret}")
j2534.PassThruDisconnect(physical_channel_id)
j2534.PassThruClose(device_id)
PassThruConnect() - Utworzenie połączenia fizycznegoPassThruLogicalDisconnect() - Zamknięcie kanału logicznegoPassThruReadMsgs() - Odczyt wiadomości z kanału